단순한 팩토리는 디자인 패턴이 아닙니다. 이는 단순히 클라이언트 코드에서 객체 생성을 분리합니다. 즉, Simple Factory는 인스턴스화 로직을 별도의 클래스로 이동하여 객체 인스턴스화를 캡슐화합니다.
간단한 팩토리는 종종 팩토리 패턴과 혼동됩니다. 차이점을 명확히 하기 위해 Simple Factory에 대해 알아보겠습니다. 또한 Simple Factory를 학습하면 Factory 패턴을 쉽게 이해할 수 있습니다.
구체적인 구현을 위한 프로그래밍은 애플리케이션 유지 관리를 매우 어렵게 만들기 때문에 피해야 합니다. 인터페이스에 프로그래밍하는 것이 항상 바람직합니다. 클라이언트 코드에서 구체적인 클래스를 인스턴스화하는 경우 Simple 팩토리가 클라이언트에서 객체 생성을 분리할 수 있으므로 Simple 팩토리가 유용합니다. 이는 우리의 애플리케이션을 더욱 확장 가능하고 유지 관리하기 쉽게 만듭니다.
버거샵 시스템을 개발하고 있습니다. 쇠고기 버거, 치킨 버거 등 다양한 버거를 만드는 시스템이 필요합니다.
첫 번째 시도는 다음과 같습니다.
// Client orders a burger Burger orderBurger(String type) { Burger burger; if (type.equals("beef")) { burger = new BeefBurger(); } else if (type.equals("chicken")) { burger = new ChickenBurger(); } else if (type.equals("fish")) { burger = new FishBurger(); } burger.prepareBun(); burger.grillPatty(); burger.addToppings(); burger.wrap(); return burger; }
문제는 인터페이스가 아닌 구현을 위해 코딩하고 있다는 것입니다. 어디? if 문을 사용하고 버거 유형을 기반으로 구체적인 클래스를 인스턴스화합니다.
왜 문제가 됩니까? 우리의 클라이언트 코드는 객체 생성과 밀접하게 결합되어 유연성이 떨어집니다!! 더 이상 생선 버거를 판매하지 않고 채식 버거를 판매하기 시작한다고 가정해 보겠습니다. 클라이언트 코드를 방문하여 수정해야 합니다. 즉, 수정을 위해 닫혀있지 않습니다.
문제를 해결하기 위해 객체 생성만 담당하는 별도의 클래스를 만들 수 있습니다. 그러면 클라이언트 코드는 객체 생성에 대해 걱정할 필요가 없으며 추상화에 의존할 수 있습니다. 이 기술은 "다양한 내용 캡슐화"로 알려져 있습니다. 구체적인 객체 인스턴스화에 대한 코드는 자주 변경될 것으로 예상하지만 prepareBun(), grillPatty(), addToppings(), Wrap() 프로세스는 미래의 모든 버거에서 동일하게 유지될 가능성이 높습니다.
Simple Factory의 장점은 다른 클래스에서 재사용이 가능하다는 것입니다. SimpleBurgerFactory.createBurger() 메소드를 사용하는 BurgerRestaurant, BurgerCateringShop과 같은 다른 클라이언트 클래스가 있을 수도 있습니다.
고객
클라이언트는 SimpleBurgerFactory를 통해 특정 버거 객체를 인스턴스화합니다. 클라이언트 관점에서 보면 어떤 콘크리트 버거가 생성될지 알 수 없습니다. 즉, 객체 생성 로직이 이제 클라이언트에서 분리되었습니다.
심플버거팩토리
이 클래스는 변화하는 것, 즉 객체 생성 로직을 캡슐화합니다! createBurger()는 클라이언트가 이 클래스를 사용하여 객체를 인스턴스화하기를 원하기 때문에 정적 메서드로 선언됩니다(물론 인스턴스화하기 전에는 인스턴스를 가질 수 없습니다!). createBurger()는 생성해야 하는 버거 유형을 결정하기 위해 BurgerType 열거형을 허용합니다.
버거
이 추상 클래스는 모든 버거 사이에 공통 인터페이스를 제공하고 기본 동작을 정의합니다.
버거 하위 클래스
콘크리트 제품은 다음과 같습니다. Burger 클래스를 확장하는 한 메서드를 재정의하여 특정 동작을 구현할 수 있습니다.
public enum BurgerType { BEEF, CHICKEN, FISH, VEGGIE }
// Abstract Product public abstract class Burger { public BurgerType burgerType; public Listtoppings = new ArrayList(); public void prepareBun() { System.out.println("Preparing a bun"); } public void grillPatty() { if (burgerType == null) { throw new IllegalStateException("pattyType is undefined"); } System.out.println("Grill a " burgerType " patty"); } public void addToppings() { for (String item : toppings) { System.out.println("Add " item); } } public void wrap() { System.out.println("Wrap a burger up"); } }
// Concrete product public class BeefBurger extends Burger { public BeefBurger() { burgerType = BurgerType.BEEF; Listitems = List.of("lettuce", "pickle slices", "tomato slice", "BBQ sauce"); toppings.addAll(items); } }
// Concrete product public class VeggieBurger extends Burger { public VeggieBurger() { burgerType = BurgerType.VEGGIE; Listitems = List.of("smoked paprika", "garlic chips", "crushed walnuts", "veggie sauce"); toppings.addAll(items); } // Concrete product can implement specific behavior that differs from other products @Override public void wrap() { System.out.println("Wrapping paper shouldn't print any meats but vegetables"); } }
// Simple factory, responsible for instantiating an object public class SimpleBurgerFactory { public static Burger createBurger(BurgerType type) { return switch (type) { case BEEF -> new BeefBurger(); case CHICKEN -> new ChickenBurger(); case FISH -> new FishBurger(); case VEGGIE -> new VeggieBurger(); default -> throw new IllegalArgumentException("unknown burger type"); }; } }
public class Client { public static void main(String[] args) { Burger burger = orderBurger(BurgerType.VEGGIE); System.out.println(burger); // Check if the object is actually veggie burger } public static Burger orderBurger(BurgerType type) { // Factory is responsible for object creation Burger burger = SimpleBurgerFactory.createBurger(type); burger.prepareBun(); burger.grillPatty(); burger.addToppings(); burger.wrap(); return burger; } }
산출:
Preparing a bun Grill a VEGGIE patty Add smoked paprika Add garlic chips Add crushed walnuts Add veggie sauce Wrapping paper shouldn't print any meats but vegetables com.factories.simpleFactory.VeggieBurger@9807454
여기에서 모든 디자인 패턴 구현을 확인할 수 있습니다.
GitHub 저장소
추신.
기술 블로그를 처음 작성하는 초보입니다. 글쓰기를 개선하기 위한 조언이 있거나 혼란스러운 점이 있으면 댓글을 남겨주세요!
읽어주셔서 감사합니다 :)
부인 성명: 제공된 모든 리소스는 부분적으로 인터넷에서 가져온 것입니다. 귀하의 저작권이나 기타 권리 및 이익이 침해된 경우 자세한 이유를 설명하고 저작권 또는 권리 및 이익에 대한 증거를 제공한 후 이메일([email protected])로 보내주십시오. 최대한 빨리 처리해 드리겠습니다.
Copyright© 2022 湘ICP备2022001581号-3