Singleton Pattern 싱글턴 패턴 GoF 디자인패턴
GoF 디자인 패턴 중 생성패턴의 하나인 Singleton 패턴에 대해 알아보도록 하겠습니다.
Singleton Pattern은 Spring bean, @Scope("singleton"), MapStruct Mapper 등 많이 사용되는 패턴 중의 하나입니다.
특징
Singleton 은 객체가 오직 한 개의 인스턴스만 갖도록 하는 패턴입니다.
Spring을 예로 들면 @Component 관련 어노테이션을 통해 Spring Container에 단 하나의 객체 인스턴스만 생성을 하고,
Inject 관련 어노테이션 (@Autowired, @Resource)을 통해 주입하여 사용하게 됩니다.
단점으로는 상속이 불가능 하기 때문에 다형성을 해치는 개념이고, 전역적인 접근을 허용하기 때문에 정보은닉을 해치는 단점이 있습니다. 그리고 멀티 쓰레드 환경에서 동시에 객체를 생성하게 되면 복수의 객체가 생성될 수 있습니다.
Singleton이지만 Singleton이 아니게 된 것 입니다.
샘플 코드
import com.google.gson.Gson;
public class SingletonGson {
private static Gson GSON;
public SingletonGson() {}
public static Gson getInstance() {
if(GSON == null) {
GSON = new Gson();
}
return GSON;
}
}
import com.google.gson.Gson;
public class SingletonPattern {
public static void main(String args[]) {
Gson gson1 = SingletonGson.getInstance();
Gson gson2 = SingletonGson.getInstance();
Gson gson3 = SingletonGson.getInstance();
System.out.println(gson1 == gson2);
System.out.println(gson2 == gson3);
}
}
실행 결과
true
true
Gson 객체의 인스턴스를 하나만 생성해서 같은 인스턴스를 공유하는 샘플 코드 입니다.
실생결과 gson1 과 gson2, gson3 가 모두 같은 인스턴스라는 결과를 확인할 수 있습니다.
static class 하고 뭐가 다르지?
사실 사용하는데는 차이가 없습니다. 둘 다 단 하나의 객체만 인스턴스화되고 그 인스턴스를 공유하죠.
하지만 static 코드는 객체지향적이지 않다는 의견이 많고, 사용하는 JVM 메모리 영역에 차이가 존재합니다.
static 변수는 프로그램이 실행되면 Class 영역 (Method Area) 에 생성되고, 어플리케이션이 종료될 때까지 유지가 됩니다.
이는 GC의 관리영역을 벗어나기 때문에 무분별 하게 사용할 경우 메모리 누수가 발생할 수 있습니다.
Singleton 패턴으로 생성할 경우 Heap 영역에 인스턴스화 되며 static 변수는 Heap 영역의 인스턴스를 가리키게 됩니다.
이는 호출되기 전까지 인스턴스를 생성하지 않기 때문에 lazy loading 이 필요한 객체 생성 시 유용합니다.
Java 메모리 구조에 대해서는 아래의 Link를 확인하세요.
Link: https://aljjabaegi.tistory.com/387