공장 방식 패턴
Factory method pattern클래스 베이스 프로그래밍에서 팩토리 메서드 패턴은 생성되는 객체의 정확한 클래스를 지정하지 않고 객체의 작성 문제를 처리하기 위해 팩토리 메서드를 사용하는 순환 패턴입니다.이는 컨스트럭터를 호출하는 것이 아니라 팩토리 메서드(인터페이스로 지정되고 자녀 클래스로 구현되거나 기본 클래스로 구현되며 파생 클래스로 선택적으로 덮어쓰기됨)를 호출하여 개체를 만듭니다.
개요
Factory Method 설계 패턴은 반복적인 설계 문제를 해결하고 유연하고 재사용 가능한 객체 지향 소프트웨어, 즉 구현, 변경, 테스트 및 재사용이 용이한 객체를 설계하는 방법을 설명하는 23개의 잘 알려진 설계 패턴 중 하나입니다.
Factory Method 설계 패턴은 다음과 같은 문제를 해결합니다.
- 서브클래스가 인스턴스화할 클래스를 재정의할 수 있도록 오브젝트를 작성하려면 어떻게 해야 합니까?
- 클래스가 인스턴스화를 서브클래스로 연기하려면 어떻게 해야 합니까?
공장 출하시 방법 설계 패턴은 이러한 문제를 해결하는 방법을 설명합니다.
- 오브젝트를 작성하기 위한 별도의 조작(출고시 방식)을 정의합니다.
- 팩토리 메서드를 호출하여 개체를 만듭니다.
이를 통해 서브클래스의 쓰기를 통해 오브젝트의 작성 방법을 변경할 수 있습니다(인스턴스화할 클래스를 재정의할 수 있습니다).
다음 UML 클래스 다이어그램도 참조하십시오.
정의.
"개체를 만들기 위한 인터페이스를 정의하되, 인스턴스화할 클래스는 하위 클래스가 결정하도록 합니다.Factory 메서드에서는 클래스가 서브클래스에 사용하는 인스턴스화를 연기할 수 있습니다.(Gang Of Four)
오브젝트를 작성하려면 컴포지팅 오브젝트에 포함시키기에는 적절하지 않은 복잡한 프로세스가 필요한 경우가 많습니다.오브젝트의 작성에 의해 코드가 크게 중복되거나 컴포지팅 오브젝트에 액세스 할 수 없는 정보가 필요하거나 충분한 추상화 수준을 제공하지 않거나 컴포지팅 오브젝트의 우려사항이 될 수 있습니다.공장 메서드 설계 패턴은 오브젝트를 작성하는 별도의 메서드를 정의함으로써 이러한 문제를 처리합니다.이러한 메서드는 서브클래스가 덮어쓰고 생성될 제품의 파생 유형을 지정할 수 있습니다.
공장 메서드 패턴은 객체 생성을 공장 메서드를 구현하여 객체를 생성하는 하위 [3]클래스에 위임하기 때문에 상속에 의존합니다.
구조.
UML 클래스 다이어그램

위의 UML 클래스 다이어그램에서는Creator
를 필요로 하는 클래스Product
오브젝트가 인스턴스화되지 않는다.Product1
직접 수업합니다.대신,Creator
별개라는 뜻하다factoryMethod()
제품 오브젝트를 생성하기 위해Creator
어떤 콘크리트 클래스가 인스턴스화되는지와 무관합니다.서브클래스Creator
인스턴스화할 클래스를 재정의할 수 있습니다.이 예에서는Creator1
서브클래스는 추상화를 구현한다.factoryMethod()
를 인스턴스화함으로써Product1
학급.
예
미로 게임은 두 가지 모드로 진행됩니다. 하나는 인접한 방과 연결된 일반 방이 있고, 다른 하나는 플레이어를 무작위로 이송할 수 있는 마법 방이 있습니다.
구조.
Room
는 최종 제품의 기본 클래스입니다(MagicRoom
또는OrdinaryRoom
).MazeGame
이러한 기본 제품을 생산하기 위한 추상 공장 방법을 선언합니다. MagicRoom
그리고.OrdinaryRoom
는 최종 제품을 구현하는 기본 제품의 하위 클래스입니다. MagicMazeGame
그리고.OrdinaryMazeGame
의 아류이다MazeGame
최종 제품을 생산하는 공장 방법의 구현.따라서, 공장 출하시의 방법에서는, 발신자가 분리됩니다).MazeGame
)를 도입하는 것으로 합니다.이것에 의해, 「신규」운용자는 용장화 되어, 오픈/클로즈 원칙을 준수할 수 있게 되어, 변경시에 최종 제품의 유연성이 향상됩니다.
구현 예시
C#
// 실제 객체의 빈 어휘 일반의 인터페이스 아이퍼슨 { 스트링 이름 가져오기(); } 일반의 학급 마을 사람 : 아이퍼슨 { 일반의 스트링 이름 가져오기() { 돌아가다 '마을 사람'; } } 일반의 학급 시티 퍼슨 : 아이퍼슨 { 일반의 스트링 이름 가져오기() { 돌아가다 '도시인'; } } 일반의 열거하다 퍼스널 타입 { 시골의, 도시의 } // </ </filters> /// 공장 구현 - 객체 작성에 사용됩니다. // </filters> 일반의 학급 공장 { 일반의 아이퍼슨 인물 취득(퍼스널 타입 유형) { 전환하다 (유형) { 사례. 퍼스널 타입.시골의: 돌아가다 신규 마을 사람(); 사례. 퍼스널 타입.도시의: 돌아가다 신규 시티 퍼슨(); 체납: 던지다 신규 지원되지 않음예외.(); } } }
위의 코드에서는 1개의 인터페이스 생성에 대해 알 수 있습니다.IPerson
두 가지 구현이 있습니다.Villager
그리고.CityPerson
에 전달된 유형에 따라Factory
오브젝트, 우리는 원래의 콘크리트 오브젝트를 인터페이스로 반환한다.IPerson
.
공장 출하시의 방법은,Factory
class. 인터페이스를 통해 클래스의 오브젝트를 만들지만 다른 한편으로 서브클래스가 인스턴스화할 클래스를 결정할 수도 있습니다.
일반의 인터페이스 IProduct { 스트링 이름 가져오기(); 부울 가격 설정(이중으로 하다 가격.); } 일반의 학급 전화 : IProduct { 사적인 이중으로 하다 _가격; 일반의 스트링 이름 가져오기() { 돌아가다 "애플 터치패드"; } 일반의 부울 가격 설정(이중으로 하다 가격.) { _가격 = 가격.; 돌아가다 진실의; } } /* Factory와 거의 마찬가지로 작성한 방법으로 작업을 하기 위한 추가 노출만 가능합니다. 일반의 추상적인 학급 Product Abstract Factory(제품 추출 공장) { 보호되고 있다 추상적인 IProduct 제품 만들기(); 일반의 IProduct Get Object(개체 취득)() // 공장 방법의 실장. { 돌아가다 이것..제품 만들기(); } } 일반의 학급 Phone Concrete Factory : Product Abstract Factory(제품 추출 공장) { 보호되고 있다 덮어쓰다 IProduct 제품 만들기() { IProduct 제품. = 신규 전화(); // 개체를 가져온 후 개체로 작업을 수행합니다. 제품..가격 설정(20.30); 돌아가다 제품.; } }
보다시피 우리는MakeProduct
콘크리트 팩토리에 있습니다.그 때문에, 간단하게 전화할 수 있습니다.MakeProduct()
그것을 통해IProduct
구체적인 공장 출하시 방법으로 객체를 가져온 후 커스텀 로직을 작성할 수도 있습니다.GetObject는 Factory 인터페이스에서 추상화됩니다.
자바
이 Java 예는 "Design Patterns"의 예와 유사합니다.
Maze Game은 Rooms를 사용하지만 구체적인 클래스를 만드는 하위 클래스에 Rooms를 만드는 책임을 부여합니다.일반 게임 모드에서는 다음 템플릿 방식을 사용할 수 있습니다.
일반의 추상적인 학급 방 { 추상적인 무효 연결하다(방 방); } 일반의 학급 매직룸 확장 방 { 일반의 무효 연결하다(방 방) {} } 일반의 학급 통상실 확장 방 { 일반의 무효 연결하다(방 방) {} } 일반의 추상적인 학급 메이즈 게임 { 사적인 최종 목록.< >방> 방 = 신규 어레이 리스트<< 고객명 >>님(); 일반의 메이즈 게임() { 방 방1 = make Room(); 방 방2 = make Room(); 방1.연결하다(방2); 방.더하다(방1); 방.더하다(방2); } 추상적인 보호되고 있다 방 make Room(); }
위의 스니펫에서는MazeGame
컨스트럭터는 몇 가지 공통 로직을 만드는 템플릿 메서드입니다.이 용어는makeRoom
다른 룸을 하위 클래스에서 사용할 수 있도록 룸 생성을 캡슐화하는 팩토리 메서드.마법의 방이 있는 다른 게임 모드를 구현하려면, 이 모드를 오버라이드하는 것으로 충분합니다.makeRoom
방법:
일반의 학급 매직메이즈 게임 확장 메이즈 게임 { @오버라이드 보호되고 있다 매직룸 make Room() { 돌아가다 신규 매직룸(); } } 일반의 학급 노멀 메이즈 게임 확장 메이즈 게임 { @오버라이드 보호되고 있다 통상실 make Room() { 돌아가다 신규 통상실(); } } 메이즈 게임 통상 게임 = 신규 노멀 메이즈 게임(); 메이즈 게임 매직 게임 = 신규 매직메이즈 게임();
PHP
PHP의 또 다른 예는 다음과 같습니다.이번에는 서브클래싱이 아닌 인터페이스 구현을 사용합니다(단, 서브클래싱을 통해서도 같은 것을 실현할 수 있습니다).공장 출하시의 메서드는 public으로 정의되어 클라이언트코드로 직접 호출할 수도 있습니다(위의 Java 예와 대조됩니다).
/* 공장 및 자동차 인터페이스 */ 인터페이스 카팩토리 { 일반의 기능. 메이커(): 차; } 인터페이스 차 { 일반의 기능. get Type(유형)(): 스트링; } /* 공장 및 자동차의 구체적인 구현 */ 학급 Sedan Factory 용구 카팩토리 { 일반의 기능. 메이커(): 차 { 돌아가다 신규 세단(); } } 학급 세단 용구 차 { 일반의 기능. get Type(유형)(): 스트링 { 돌아가다 '세단'; } } /* 클라이언트 */ 공장 출하시 = 신규 Sedan Factory(); 차비 = 공장 출하시->메이커(); 인쇄물 차비->get Type(유형)();
파이썬
Java의 예시와 동일합니다.
부터 abc 수입품 ABC, 추상적 방법 학급 메이즈 게임(ABC): 방어하다 __init__(자신) -> 없음.: 자신.방 = [] 자신._thead_rooms_rooms() 방어하다 _thead_rooms_rooms(자신) -> 없음.: 방1 = 자신.방을 만들다() 방2 = 자신.방을 만들다() 방1.연결하다(방2) 자신.방.추가하다(방1) 자신.방.추가하다(방2) 방어하다 놀고(자신) -> 없음.: 인쇄물(f"사용하는 플레이{자신.방[0]}") @http 방법 방어하다 방을 만들다(자신): 올리다 구현되지 않은 오류(「이것을 실장할 필요가 있습니다.) 학급 매직메이즈 게임(메이즈 게임): 방어하다 방을 만들다(자신) -> '매직룸': 돌아가다 매직룸() 학급 노멀 메이즈 게임(메이즈 게임): 방어하다 방을 만들다(자신) -> "일반실": 돌아가다 통상실() 학급 방(ABC): 방어하다 __init__(자신) -> 없음.: 자신.접속_실 = [] 방어하다 연결하다(자신, 방: '방') -> 없음.: 자신.접속_실.추가하다(방) 학급 매직룸(방): 방어하다 __str__(자신) -> 스트레이트: 돌아가다 '마법의 방' 학급 통상실(방): 방어하다 __str__(자신) -> 스트레이트: 돌아가다 "일반실" 통상 게임 = 노멀 메이즈 게임() 통상 게임.놀고() 매직 게임 = 매직메이즈 게임() 매직 게임.놀고()
사용하다
- ADO.NET에서는 IDbCommand.CreateParameter는 공장 메서드를 사용하여 병렬 클래스 계층을 연결하는 예입니다.
- QT에서 QMain Window::create Popup Menu는 애플리케이션 코드로 덮어쓸 수 있는 프레임워크로 선언된 공장 메서드입니다.
- Java에서는 javax.xml.parsers 패키지에 javax.xml.parsers 등 여러 팩토리가 사용됩니다.Document Builder Factory 또는 javax.xml.pars.SAXParser Factory 。
- HTML5 DOM API에서 Document 인터페이스에는 HTMLlement 인터페이스의 특정 요소를 작성하기 위한 createElement 팩토리 메서드가 포함되어 있습니다.
「 」를 참조해 주세요.
- 영향력이 큰 책인 디자인 패턴스
- 설계 패턴, 일반적인 설계 패턴 개요
- 추상적인 공장 패턴, 공장 방법을 사용하여 구현되는 패턴
- 빌더 패턴, 다른 크레이셔널 패턴
- 공장 메서드를 호출할 수 있는 템플릿 메서드 패턴
- Joshua Bloch의 정적 공장법 아이디어는 Design Patterns에 직접적인 등가물은 없다고 합니다.
레퍼런스
- ^ Erich Gamma, Richard Helm, Ralph Johnson, John Vlissides (1994). Design Patterns: Elements of Reusable Object-Oriented Software. Addison Wesley. pp. 107ff. ISBN 0-201-63361-2.
{{cite book}}
: CS1 maint: 여러 이름: 작성자 목록(링크) - ^ "The Factory Method design pattern - Problem, Solution, and Applicability". w3sDesign.com. Retrieved 2017-08-17.
- ^ Freeman, Eric; Freeman, Elisabeth; Kathy, Sierra; Bert, Bates (2004). Hendrickson, Mike; Loukides, Mike (eds.). Head First Design Patterns (paperback). Vol. 1. O'REILLY. p. 162. ISBN 978-0-596-00712-6. Retrieved 2012-09-12.
- ^ "The Factory Method design pattern - Structure and Collaboration". w3sDesign.com. Retrieved 2017-08-12.
- Martin Fowler; Kent Beck; John Brant; William Opdyke; Don Roberts (June 1999). Refactoring: Improving the Design of Existing Code. Addison-Wesley. ISBN 0-201-48567-2.
- Gamma, Erich; Helm, Richard; Johnson, Ralph; Vlissides, John (1994). Design Patterns: Elements of Reusable Object-Oriented Software. Addison-Wesley. ISBN 0-201-63361-2.
- Cox, Brad J. (1986). Object-oriented programming: an evolutionary approach. Addison-Wesley. ISBN 978-0-201-10393-9.
- Cohen, Tal; Gil, Joseph (2007). "Better Construction with Factories" (PDF). Journal of Object Technology. Bertrand Meyer. 6 (6): 103. doi:10.5381/jot.2007.6.6.a3. Retrieved 2007-03-12.
외부 링크
