티스토리 뷰
싱글톤 패턴(singleton)
오직 1개의 인스턴스만 제공이 필요할 때, 그 글로벌한 인스턴스에 접근이 필요할 때(접근 방법을 제공해야 함)
예로 들어 설정 정도가 있다.
public class Object1 {
private static Object1 instance;
private Object1(){}
public static Object1 getInstance() {
if(instance == null){
instance = new Object1();
}
return instance;
}
}
Object1안에 instance라는 이름의 object1 타입의 객체를 만들어둡니다.
private 접근할 수 없으며 생성자도 private이라 직접 접근할 수 없습니다.
getInstance로만 접근할 수 있습니다.
'== null' 일시 인스턴스를 생성하고
반대의 경우 존재하는 객체를 반환합니다.
하지만 멀티스레드 환경에서는 안전을 보장하지 못합니다.
public static synchronized Object1 getInstance() {
if(instance == null){
instance = new Object1();
}
return instance;
}
synchronized 키워드를 삽입하여 한번에 하나의 스레드만 들어올 수 있게 됩니다.
하지만 성능부하가 있을 수 있습니다.
public class Object1 {
private static final Object1 INSTANCE = new Object1();
private Object1(){}
public static Object1 getInstance() {
return INSTANCE;
}
}
eager initialization(이른 초기화) 또 하나의 방법입니다.
미리 객체를 생성합니다.
public class Object1 {
private static class ObjectHolder {
private static final Object1 INSTANCE = new Object1();
}
public static Object1 getInstance() {
return ObjectHolder.INSTANCE;
}
}
이른 초기화를 피하며 멀티스레드 환경에서도 안전하며
싱글톤 조건에도 부합한 방법입니다.
Constructor constructor = SingletonObj.class.getDeclaredConstructor();
constructor.setAccessible(true);
SingletonObj singletonObj = (SingletonObj) constructor.newInstance();
SingletonObj singletonObj2 = SingletonObj.getInstance();
System.out.println(singletonObj == singletonObj2);
다만 리플렉션 기능을 사용하여 생성자를 이용하여 인스턴스를 생성할 수 있습니다.
위에서는 Object1으로 했지만 새로운 클래스를 만들어서 한 것입니다.
내부에는 동일한 코드를 가지고 있습니다.
팩토리 메서드 패턴(Factory method)
다양한 구현체가 있고 그중 특정한 구현체를 만들 수 있는 다양한 팩토리 제공
객체를 생성을 위한 new키워드 사용을 하위 클래스에 위임(어떤 인스턴스를 생성할지 subClass가 결정)
확장 중 기본이 되는 코드들의 변경이 없습니다.
확장에는 열려있고 변경에는 닫힌 코드를 만들 수 있습니다.(OCP)
코드를 수정하지 않고 새로운 제품군을 만들어낼 수 있습니다.

책을 주문하면 만들어서 주는 기능입니다.

팩토리의 제일 부모 BookFactory입니다.
팩토리의 기능들이 적혀있습니다.

만화책, 스포츠 책 든 모든 종류의 책을 만들어주는 팩토리의 공통기능은
위 추상 클래스에서 모두 작성하였습니다.


실제 인스턴스로 생성될 팩토리입니다.
new키워드 사용이 위임될 층입니다, 각각 카테고리에 적합한 책을 반환합니다.
상위 인터페이스와 추상 클래스는 더 많은 팩토리의 추가에도 코드의 변경이 없습니다.
public class DefaultBook {
private String name;
private String categori;
@Override
public String toString() {
return "DefaultBook{" +
"name='" + name + '\'' +
", categori='" + categori + '\'' +
'}';
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getCategori() {
return categori;
}
public void setCategori(String categori) {
this.categori = categori;
}
}
추상 팩토리에서는 DefaultBook타입을 반환합니다.
만화책 팩토리는 만화책을 반환, 스포츠 책 팩토리는 스포츠 책을 반환하니
모든 종류의 슈퍼클래스가 되는 타입을 반환합니다.
public class AnnieBook extends DefaultBook{
public AnnieBook(){
setName("원피스");
setCategori("만화책");
}
public void printForAnnie(){
System.out.println("anniebook만의 기능입니다.");
}
}
실제 반환되는 책입니다.
슈퍼클래스에서 모든 공통 타입이 선언되어있어
슈퍼클래스의 기능만 사용하면 됩니다.
public class Client {
public static void main(String[] args) {
AnnieBook book = (AnnieBook) new AnnieBookFactory().orderBook("주문자 이정석");
Sportsbook book2 = (Sportsbook) new SportsBookFactory().orderBook("주문자 정상환");
System.out.println(book);
System.out.println(book2);
book.printForAnnie();
book2.printForSport();
}
}
실제 사용 코드입니다.
스프링같이 DI개념을 사용하는 프레임워크를 사용할 경우에는
factory를 생성하지 않고 주입받아 orderBook을 사용하면 될 것 같습니다.
'Java & Kotlin' 카테고리의 다른 글
| JVM (0) | 2021.12.21 |
|---|---|
| 'JWT'를 'JAVA'로 만들어보기 (0) | 2021.12.21 |
| java 직렬화(Serialize) (0) | 2021.10.20 |
| 자바 Collection (0) | 2021.10.19 |
| 자바 상속 (java Inheritance) (0) | 2021.10.03 |
- Total
- Today
- Yesterday
- boot
- 관계설정
- jre
- mappedby
- 자바
- jre8
- boot 일대다
- 백엔드
- jvm
- JDK
- JDK8
- java8
- 문제
- 프로그래머
- 자사서비스
- 스타트업
- jdk11
- jre11
- 스택
- 백준 제로 자바
- 다대일
- springboot
- Spring
- 백준 제로
- 알고리즘
- 백준
- ㅃ
- JPA
- 코딩테스트
- 개발자채용
| 일 | 월 | 화 | 수 | 목 | 금 | 토 |
|---|---|---|---|---|---|---|
| 1 | 2 | 3 | 4 | 5 | 6 | 7 |
| 8 | 9 | 10 | 11 | 12 | 13 | 14 |
| 15 | 16 | 17 | 18 | 19 | 20 | 21 |
| 22 | 23 | 24 | 25 | 26 | 27 | 28 |