对象对具体类的依赖
Posted
技术标签:
【中文标题】对象对具体类的依赖【英文标题】:object dependency on to concrete classes 【发布时间】:2021-04-25 13:18:45 【问题描述】:我正在尝试理解抽象工厂模式,虽然这很难。我从 Head First Design Patterns 书中看到了以下示例,试图描述依赖关系以及为什么依赖是不好的。但是,我不明白该代码示例的以下说法。
因为对比萨饼具体实现的任何更改都会影响
DependentPizzaStore
,我们说DependentPizzaStore
“取决于”披萨 实现。
我真的不明白它如何影响刚刚由new
s 启动并使用bake
、cut
等方法的类。 DependentPizzaStore
对具体实现一无所知。
public class DependentPizzaStore
public Pizza createPizza(String style, String type)
Pizza pizza = null;
if (style.equals("NY"))
if (type.equals("cheese"))
pizza = new NYStyleCheesePizza();
else if (type.equals("veggie"))
pizza = new NYStyleVeggiePizza();
else if (type.equals("clam"))
pizza = new NYStyleClamPizza();
else if (type.equals("pepperoni"))
pizza = new NYStylePepperoniPizza();
else if (style.equals("Chicago"))
if (type.equals("cheese"))
pizza = new ChicagoStyleCheesePizza();
else if (type.equals("veggie"))
pizza = new ChicagoStyleVeggiePizza();
else if (type.equals("clam"))
pizza = new ChicagoStyleClamPizza();
else if (type.equals("pepperoni"))
pizza = new ChicagoStylePepperoniPizza();
else
System.out.println("Error: invalid type of pizza");
return null;
pizza.prepare();
pizza.bake();
pizza.cut();
pizza.box();
return pizza;
【问题讨论】:
【参考方案1】:DependentPizzaStore
需要明确了解所有实现才能初始化它们。因此DependentPizzaStore
依赖于这些实现并紧密耦合。如果这些实现的构造函数中的任何一个要更改,那么您还需要更改 DependentPizzaStore
抽象工厂将允许您提供一个接口来创建相关或依赖对象的系列,而无需指定它们的具体类。
因为你的例子也有不同风格的披萨
public interface PizzaFactory
string getStyle();
Pizza createPizza(String type);
那么对于不同的风格就需要不同的工厂。
public class NYStylePizzaFactory implements PizzaFactory
public string getStyle() return "NY";
public Pizza createPizza(String type)
Pizza pizza = null;
if (type.equals("cheese"))
pizza = new NYStyleCheesePizza();
else if (type.equals("veggie"))
pizza = new NYStyleVeggiePizza();
else if (type.equals("clam"))
pizza = new NYStyleClamPizza();
else if (type.equals("pepperoni"))
pizza = new NYStylePepperoniPizza();
if(pizza == null)
//...throw?
return pizza;
public class ChicagoStylePizzaFactory implements PizzaFactory
public string getStyle() return "Chicago";
public Pizza createPizza(String type)
if (type.equals("cheese"))
pizza = new ChicagoStyleCheesePizza();
else if (type.equals("veggie"))
pizza = new ChicagoStyleVeggiePizza();
else if (type.equals("clam"))
pizza = new ChicagoStyleClamPizza();
else if (type.equals("pepperoni"))
pizza = new ChicagoStylePepperoniPizza();
if(pizza == null)
//...throw?
return pizza;
DependentPizzaStore
现在可以将创建披萨的任务委托给工厂,而无需了解任何有关实施细节。
public class DependentPizzaStore
List<PizzaFactory> factories;
public DependentPizzaStore(List<PizzaFactory> factories)
this.factories = factories;
public Pizza createPizza(String style, String type)
Pizza pizza = null;
for (PizzaFactory factory : factories)
if (factory.getStyle().equals(style))
pizza = factory.createPizza(type);
break;
if (pizza == null)
System.out.println("Error: invalid type of pizza");
return null;
pizza.prepare();
pizza.bake();
pizza.cut();
pizza.box();
return pizza;
任何其他样式都不会影响或导致商店发生变化。工厂制作披萨的方式的任何变化也不会影响或导致商店发生变化。
因此,存储依赖于抽象而不是具体。
【讨论】:
我们可以说构造函数的签名是一个实现细节吗?因为在您的第一句话中,您说 DependentPizzaStore 需要明确了解所有实现。 @snr 是的,知道构造函数签名是一个实现细节以上是关于对象对具体类的依赖的主要内容,如果未能解决你的问题,请参考以下文章