Factory 패턴

팩토리 메서드 패턴(Factory method pattern)은 객체지향 디자인 패턴이다. Factory method는 부모(상위) 클래스에 알려지지 않은 구체 클래스를 생성하는 패턴이며. 자식(하위) 클래스가 어떤 객체를 생성할지를 결정하도록 하는 패턴이기도 하다.

장점

싱글톤 패턴 : static을 사용한 효과로 객체를 생성하지 않고도 패턴을 사용가능.

예제

피자 가게에서 피자를 주문하고 그 가격을 출력해주는 예제

객체 생성 로직을 어디서 하는가 ?

Factory 패턴을 사용하지 않은 예제

void main(){
	var userSelectedPizza = PizzaType.HamMushroom;
	Pizza pizza;
	switch (userSelectedPizza){
		case PizzaType.HamMushroom;
			pizza = HamAndMushroomPizza();
			break;
		case PizzaType.Deluxe;
			pizza = DeluxePizza();
			break;
		case PizzaType.Seafood;
			pizza = SeafoodPizza();
			break;
	}
	print(pizza.getPrice());
}
// 피자 종류
enum PizzaType { HamMushroom, Deluxe, Seafood }

abstract class Pizza{
	double getPrice();
}

class HamAndMushroomPizza implements Pizza{
	double price = 10.5;
	@override
	double getPrice(){
		return price;
	}
}

class DeluxePizza implements Pizza{
	double price = 5.5;
	@override
	double getPrice(){
		return price;
	}
}

class SeafoodPizza implements Pizza{
	double price = 7.8;
	@override
	double getPrice(){
		return price;
	}
}

Factory 패턴을 사용한 예제

void main(){
	var userSelectedPizza = PizzaType.HamMushroom;
	print(Pizza.pizzaFactory(userSelectedPizza).getPrice());
}
// 피자 종류
enum PizzaType { HamMushroom, Deluxe, Seafood }

abstract class Pizza{
	double getPrice();
	// 팩토리 패턴
	static pizzaFactory(PizzaType type){
		switch (userSelectedPizza){
		case PizzaType.HamMushroom;
			return HamAndMushroomPizza();
			break;
		case PizzaType.Deluxe;
			return DeluxePizza();
			break;
		case PizzaType.Seafood;
			return SeafoodPizza();
			break;
		}
	}
}

class HamAndMushroomPizza implements Pizza{
	double price = 10.5;
	@override
	double getPrice(){
		return price;
	}
}

class DeluxePizza implements Pizza{
	double price = 5.5;
	@override
	double getPrice(){
		return price;
	}
}

class SeafoodPizza implements Pizza{
	double price = 7.8;
	@override
	double getPrice(){
		return price;
	}
}

로직 변경

DeluxePizza 객체 생성할때 orderNumber가 필요하다고 수정

class DeluxePizza implements Pizza{
	double price = 5.5;
	String orderNumber;
	DeluxePizza(this.orderNumber);
	@override
	double getPrice(){
		return price;
	}
}

Factory 패턴을 사용하지 않은 예제

void main(){
	var userSelectedPizza = PizzaType.HamMushroom;
	Pizza pizza;
	var orderNumber = '1234';
	switch (userSelectedPizza){
		case PizzaType.HamMushroom;
			pizza = HamAndMushroomPizza();
			break;
		case PizzaType.Deluxe;
			pizza = DeluxePizza(orderNumber);
			break;
		case PizzaType.Seafood;
			pizza = SeafoodPizza();
			break;
	}
	print(pizza.getPrice());
}

Factory 패턴을 사용한 예제

void main(){
	var userSelectedPizza = PizzaType.HamMushroom;
	String orderNumber = '1234';
	print(Pizza.pizzaFactory(userSelectedPizza,orderNumber).getPrice());
}
// 피자 종류
enum PizzaType { HamMushroom, Deluxe, Seafood }

abstract class Pizza{
	double getPrice();
	// 팩토리 패턴
	static pizzaFactory(PizzaType type, String orderNumber){
		switch (userSelectedPizza){
		case PizzaType.HamMushroom;
			return HamAndMushroomPizza();
			break;
		case PizzaType.Deluxe;
			return DeluxePizza(orderNumber);
			break;
		case PizzaType.Seafood;
			return SeafoodPizza();
			break;
		}
	}
}

Factory 패턴을 사용한 예제에서 Map 타입으로 데이터 넘겨주기

void main(){
	var userSelectedPizza = PizzaType.HamMushroom;
	String orderNumber = '1234';
	Map<String, dynamic> json = {
		'type': PizzaType.HamMushroom,
		'orderNumber' : '1234',
	}
	print(Pizza.pizzaFactory(json).getPrice());
}
// 피자 종류
enum PizzaType { HamMushroom, Deluxe, Seafood }

abstract class Pizza{
	double getPrice();
	// 팩토리 패턴
	static pizzaFactory(Map<String, dynamic> json){
		switch (json['type'] as PizzaType){
		case PizzaType.HamMushroom;
			return HamAndMushroomPizza();
			break;
		case PizzaType.Deluxe;
			return DeluxePizza(json['orderNumber'] as String);
			break;
		case PizzaType.Seafood;
			return SeafoodPizza();
			break;
		}
	}
}

Factory 패턴을 사용한 예제에서 Map 타입으로 데이터 넘겨줄때 Factory 타입으로 리턴

void main(){
	var userSelectedPizza = PizzaType.HamMushroom;
	String orderNumber = '1234';
	Map<String, dynamic> json = {
		'type': PizzaType.HamMushroom,
		'orderNumber' : '1234',
	}
	print(Pizza.fromJson(json).getPrice());
}
// 피자 종류
enum PizzaType { HamMushroom, Deluxe, Seafood }

abstract class Pizza{
	double getPrice();
	// 팩토리 패턴
	Factory Pizza.fromJson(Map<String, dynamic> json){
		switch (json['type'] as PizzaType){
		case PizzaType.HamMushroom;
			return HamAndMushroomPizza();
			break;
		case PizzaType.Deluxe;
			return DeluxePizza(json['orderNumber'] as String);
			break;
		case PizzaType.Seafood;
			return SeafoodPizza();
			break;
		default:
			return SeafoodPizza();
		}
	}
}

참고

https://www.youtube.com/watch?v=ZikfiBnFMk8 

 

728x90

'Study > Flutter' 카테고리의 다른 글

[Flutter] Provider pattern (bloc -> provider )  (0) 2021.06.16
[Flutter] Stateful widget  (0) 2021.06.14
[UI초급] Container, materialApp, Scaffold  (0) 2021.06.07

+ Recent posts