컴공생 누르지 마세요! 컴공생 울어요.

디자인 패턴 (1) 싱글톤 패턴 본문

CS STUDY/디자인 패턴

디자인 패턴 (1) 싱글톤 패턴

당도최고치악산멜론 2023. 3. 14. 22:16

싱글톤 패턴

  • 하나의 클래스에 오직 하나의 인스턴스만 가지는 패턴
  • 데이터베이스 연결 모듈에 많이 사용
  • 하나의 인스턴스를 만들어 놓고 해당 인스턴스를 다른 모듈들이 공유하며 사용 ➡️ 인스턴스 생성 비용 감소
  • 단점 - 의존성이 높아짐

자바스크립트의 싱글톤 패턴

  • 리터럴 {} 또는 new Object로 객체를 생성하게 되면 다른 어떤 객체와도 같지 않기 때문에 이 자체만으로 싱글톤 패턴 구현 가능
  • 싱글톤 패턴 구현 예시 1
const obj = {
    a: 27
}
const obj2 = {
    a: 27
}
console.log(obj === obj2)
// false
  • 싱글톤 패턴 구현 예시 2
    • Singleton.instance라는 하나의 인스턴스를 가지는 Singleton 클래스 구현
    • a와 b는 하나의 인스턴스를 가짐
class Singleton {
    constructor() {
        if (!Singleton.instance) {
            Singleton.instance = this
        }
        return Singleton.instance
    }
    getInstance() {
        return this 
    }
}
const a = new Singleton()
const b = new Singleton() 
console.log(a === b) // true

데이터베이스 연결 모듈

  • 싱글톤 패턴은 데이터베이스 연결 모듈에 많이 사용
  • 예시
    • DB.instance라는 하나의 인스턴스를 기반으로 a, b를 생성
    • 데이터베이스 연결에 관한 생성 비용 감소
const URL = 'mongodb://localhost:27017/kundolapp' 
const createConnection = url => ({"url" : url})    
class DB {
    constructor(url) {
        if (!DB.instance) { 
            DB.instance = createConnection(url)
        }
        return DB.instance
    }
    connect() {
        return this.instance
    }
}
const a = new DB(URL)
const b = new DB(URL) 
console.log(a === b) // true

자바에서의 싱글톤 패턴

class Singleton {
    private static class singleInstanceHolder {
        private static final Singleton INSTANCE = new Singleton();
    }
    public static Singleton getInstance() {
        return singleInstanceHolder.INSTANCE;
    }
}

public class HelloWorld{ 
     public static void main(String []args){ 
        Singleton a = Singleton.getInstance(); 
        Singleton b = Singleton.getInstance(); 
        System.out.println(a.hashCode());
        System.out.println(b.hashCode());  
        if (a == b){
         System.out.println(true); 
        } 
     }
}
/*
705927765
705927765
true

mongoose의 싱글톤 패턴

  • 실제로 Node.js에서 MongoDB 데이터베이스를 연결할 때 쓰는 mongoose 모듈에서 싱글톤 패턴을 볼 수 있음
  • mongoose의 데이터베이스를 연결할 때 쓰는 connect()라는 함수는 싱글톤 인스턴스를 반환

MySQL의 싱글톤 패턴

  • Node.js에서 MySQL 데이터베이스를 연결할 때도 싱글톤 패턴 사용
  • 메인 모듈에서 데이터베이스 연결에 관한 인스턴스를 정의하고, 다른 모듈들에서 해당 인스턴스를 기반으로 쿼리를 보내는 형식 

싱글톤 패턴의 단점

  • TDD(Test Driven Development)를 할 때 걸림돌이 됨
    • TDD를 할 때 단위 테스트를 주로 하는데, 단위 테스트는 테스트가 서로 독립적이어야 하며 테스트를 어떤 순서로든 실행할 수 있어야 함
    • but 싱글톤 패턴은 미리 생성된 하나의 인스턴스를 기반으로 구현하는 패턴이므로, 각 테스트마다 '독립적인' 인스턴스를 만들기가 어려움

의존성 주입

  • 싱글톤 패턴은 모듈 간의 결합을 강하게 만들 수 있음
  • ➡️ 의존성 주입 (DI, Dependency Injection)을 통해 모듈 간의 결합을 좀 더 느슨하게 만들 수 있음
  • 메인 모듈이 직접 다른 하위 모듈에 대한 의존성을 주기보다는, 중간에 의존성 주입자가 이 부분을 가로채서 메인 모듈이 간접적으로 의존성을 주입하는 방식
  • 메인 모듈(상위 모듈)은 하위 모듈에 대한 의존성이 떨어지게 됨 == '디커플링이 된다'고도 함
  • 참고)
    • 의존성 == 종속성
    • A가 B에 의존성이 있다 == B가 변경되면 A도 변경되어야 함

의존성 주입의 장점

  • 모듈들을 쉽게 교체할 수 있는 구조가 되어 테스팅하기 쉽고, 마이그레이션(소프트웨어를 다른 시스템으로 이동)도 수월해짐
  • 구현 시 추상화 레이어를 넣고 이를 기반으로 구현체를 넣어줌
  • ➡️ 애플리케이션 의존성 방향이 일관됨, 애플리케이션을 쉽게 추론할 수있음,  모듈 간 관계들이 좀 더 명확해짐

의존성 주입의 단점

  • 모듈들이 더욱더 분리 ➡️ 클래스 수가 늘어남 ➡️ 복잡성 증가 & 약간의 런타임 패널티 발생

의존성 주입 원칙

  • 의존성 주입은 의존성 주입 원칙을 지키며 만들어야 함
  • 원칙: 상위 모듈은 하위 모듈에서 어떠한 것도 가져오지 않아야 함. 둘 다 추상화에 의존해야 하며, 이때 추상화는 세부 사항에 의존하지 말아야 함.

'CS STUDY > 디자인 패턴' 카테고리의 다른 글

디자인 패턴 (2) 팩토리 패턴  (0) 2023.03.20
디자인 패턴 (0) 디자인 패턴  (0) 2023.03.14
Comments