装饰器模式
之前我们说过软件设计模式的一个典型特征就是 使用面向接口而不是继承的编程 但是有种情况是特殊的 例如我们的装饰器模式 之所以需要装饰器模式 是因为需要运行时对某个类进行修饰 由于我们设计模式的准则是开放-关闭原则 即扩展性要较高 并且关闭修改 即我们肯定是不能够修改基类的 还要能增加新的特性 这就是为什么代码中不论是Beverage(饮料)还是Condiment(配料) 都需要一个共同的基类 因为要想不修改底层代码 还要增加新的特性 那么这不就是类继承的用法吗 虽然设计模式中我们不推荐使用继承 但要因事物而变 不能固定思维 通过使用继承我们可以将配料和饮料都定为同一类型 这样调用父类的方法就没有问题 最后通过类似于递归的方式 我们可以得到最终的结果 并且可以很好的保持运行时的扩展 可以可以看到我们的main方法中可以叠加不同种类的配料 这就达到了扩展 并且如果我们想增加一个配方 那么我们只需要再继承一个配料基类 或者 饮料基类 而不用改变基类的任何代码 然后最后在main方法中加以包装即可
/**
* @Title: StarBuzzTest.java
* @Package
* @Description: TODO(用一句话描述该文件做什么)
* @author Lustre
* @date 2019年12月8日
* @version V1.0
*/
/**
* @author Nigel
* @version 创建文件时间:2019年12月8日 下午7:36:30
*/
/**
* @ClassName: StarBuzzTest
* @Description: TODO(这里用一句话描述这个类的作用)
* @author Nigel
* @date 2019年12月8日
*
*/
/**
*
* @ClassName: Beverage
* @Description: 定义一个抽象基类 之所以这里用基类而不是接口 是因为调料必须和饮料是同一个基类! 不然装饰器模式就是空谈
* @author Nigel
* @date 2019年12月8日
*
*/
abstract class Beverage{
protected String description;
public String getDescription() {
return description;
}
/**
*
* @Title: cost
* @Description: 这个cost方法是需要被所有继承的实体类所重写的 因为每个实体必定有一个价钱 并且价钱也是不一致的
* @return
* @return Double
* @throws
*/
abstract Double cost();
}
/**
*
* @ClassName: CondimentDecorator
* @Description: 调料必须继承饮料类 这样才能发挥装饰类的特点!
* @author Nigel
* @date 2019年12月8日
*
*/
abstract class CondimentDecorator extends Beverage{
protected Beverage superClassBeverage;
/**
*
* <p>Title: getDescription</p>
* <p>Description: 每个调料对应的修饰自然也是不一样的
* @return
* @see Beverage#getDescription()
*/
public abstract String getDescription();
}
/**
*
* @ClassName: Espresso
* @Description: 此时为实体类 即实体饮料
* @author Nigel
* @date 2019年12月8日
*
*/
class Espresso extends Beverage {
public Espresso() {
// TODO Auto-generated constructor stub
description = "Espresso";
}
@Override
Double cost() {
// TODO Auto-generated method stub
return 1.99;
}
}
class HouseBlend extends Beverage {
/**
* 创建一个新的实例 HouseBlend.
*
*/
public HouseBlend() {
// TODO Auto-generated constructor stub
description = "HouseBlend";
}
@Override
Double cost() {
// TODO Auto-generated method stub
return .89;
}
}
class DarkRoast extends Beverage {
/**
* 创建一个新的实例 DarkRoast.
*
*/
public DarkRoast() {
// TODO Auto-generated constructor stub
description = "DarkRoast";
}
@Override
Double cost() {
// TODO Auto-generated method stub
return .99;
}
}
class Decaf extends Beverage {
/**
* 创建一个新的实例 Decaf.
*
*/
public Decaf() {
// TODO Auto-generated constructor stub
description = "Decaf";
}
@Override
Double cost() {
// TODO Auto-generated method stub
return 1.05;
}
}
//接下来让调料进行实例化 其基类也是Beverage
class Mocha extends CondimentDecorator {
/**
* 创建一个新的实例 Mocha. 需要提供一个参数来附加到对应的饮料实体上
*
*/
public Mocha(Beverage beverage) {
// TODO Auto-generated constructor stub
superClassBeverage = beverage;
}
/**
* <p>Title: getDescription</p>
* <p>Description:之所以要重写getDescription 是因为对于调料而言 我们是要叠加上去的 所以还需要返回上级的描述!
* @return
* @see CondimentDecorator#getDescription()
*/
@Override
public String getDescription() {
// TODO Auto-generated method stub
return superClassBeverage.getDescription() + "Mocha";
}
/**
* <p>Title: cost</p>
* <p>Description: </p>
* @return
* @see Beverage#cost()
*/
@Override
Double cost() {
// TODO Auto-generated method stub
return superClassBeverage.cost() + .20;
}
}
class Milk extends CondimentDecorator {
/**
* 创建一个新的实例 Milk.
*
*/
public Milk(Beverage beverage) {
// TODO Auto-generated constructor stub
superClassBeverage = beverage;
}
@Override
public String getDescription() {
// TODO Auto-generated method stub
return superClassBeverage.description + "Milk";
}
@Override
Double cost() {
// TODO Auto-generated method stub
return superClassBeverage.cost() + .10;
}
}
class SoyaBean extends CondimentDecorator {
/**
* 创建一个新的实例 SoyaBean.
*
*/
public SoyaBean(Beverage beverage) {
// TODO Auto-generated constructor stub
superClassBeverage = beverage;
}
@Override
public String getDescription() {
// TODO Auto-generated method stub
return superClassBeverage + "SoyaBean";
}
@Override
Double cost() {
// TODO Auto-generated method stub
return superClassBeverage.cost() + .15;
}
}
class Whip extends CondimentDecorator {
/**
* 创建一个新的实例 Whip.
*
*/
public Whip(Beverage beverage) {
// TODO Auto-generated constructor stub
superClassBeverage = beverage;
}
@Override
public String getDescription() {
// TODO Auto-generated method stub
return superClassBeverage.getDescription() + "Whip";
}
/**
*
* <p>Title: cost</p>
* <p>Description: 以一种递归的方式来计算cost价格
* @return
* @see Beverage#cost()
*/
@Override
Double cost() {
// TODO Auto-generated method stub
return superClassBeverage.cost() + .10;
}
}
public class StarBuzzTest {
/**
* @Title: main
* @Description: TODO
* @param args
* @return void
* @throws
*/
public static void main(String[] args) {
//进行测试
System.out.print("不加配料的情况下:");
Beverage decafBeverage = new Decaf();//实例化一个decaf低咖啡因
System.out.println(decafBeverage.getDescription());//打印一下description
System.out.print("价钱:");
System.out.println(decafBeverage.cost());
//加上Milk后的描述和价钱
System.out.print("加Milk后的情况:");
CondimentDecorator decafWithMilk = new Milk(decafBeverage);
System.out.println( decafWithMilk.getDescription() );
System.out.print("价钱:");
System.out.printf("%.2f\n", decafWithMilk.cost());
//加Mocha后的情况
CondimentDecorator decafWithMilkAndMocha = new Mocha(decafWithMilk);
System.out.printf("再加上Mocha后的情形:");
System.out.println(decafWithMilkAndMocha.getDescription());
System.out.print("价钱:");
System.out.println(decafWithMilkAndMocha.cost());
}
}
为Beverage加size1(大杯 中杯 小杯)之后的修改代码 我们只需要修改对应的配料的cost方法后
/**
* @Title: StarBuzzTest.java
* @Package
* @Description: TODO(用一句话描述该文件做什么)
* @author Lustre
* @date 2019年12月8日
* @version V1.0
*/
/**
* @author Nigel
* @version 创建文件时间:2019年12月8日 下午7:36:30
*/
/**
* @ClassName: StarBuzzTest
* @Description: TODO(这里用一句话描述这个类的作用)
* @author Nigel
* @date 2019年12月8日
*
*/
/**
*
* @ClassName: Beverage
* @Description: 定义一个抽象基类 之所以这里用基类而不是接口 是因为调料必须和饮料是同一个基类! 不然装饰器模式就是空谈
* @author Nigel
* @date 2019年12月8日
*
*/
abstract class Beverage{
protected String description;
protected final static Integer BIG_SIZE = 9;
protected final static Integer SMALL_SIZE = 3;
protected final static Integer MEDIUM_SIZE = 6;
protected Integer size;
public Integer getSize() {
return this.size;
}
public String getDescription() {
return description;
}
/**
*
* @Title: cost
* @Description: 这个cost方法是需要被所有继承的实体类所重写的 因为每个实体必定有一个价钱 并且价钱也是不一致的
* @return
* @return Double
* @throws
*/
abstract Double cost();
}
/**
*
* @ClassName: CondimentDecorator
* @Description: 调料必须继承饮料类 这样才能发挥装饰类的特点!
* @author Nigel
* @date 2019年12月8日
*
*/
abstract class CondimentDecorator extends Beverage{
protected Beverage superClassBeverage;
/**
*
* <p>Title: getDescription</p>
* <p>Description: 每个调料对应的修饰自然也是不一样的
* @return
* @see Beverage#getDescription()
*/
public abstract String getDescription();
}
/**
*
* @ClassName: Espresso
* @Description: 此时为实体类 即实体饮料
* @author Nigel
* @date 2019年12月8日
*
*/
class Espresso extends Beverage {
public Espresso() {
// TODO Auto-generated constructor stub
description = "Espresso";
size = Beverage.MEDIUM_SIZE;//默认中杯
}
/**
*
* 创建一个新的实例 Espresso. 可以指定对应的是大杯还是小杯
*
* @param size
*/
public Espresso(Integer size) {
this.size = size;
description = "Espresso";
}
@Override
Double cost() {
// TODO Auto-generated method stub
return 1.99;
}
}
class HouseBlend extends Beverage {
/**
* 创建一个新的实例 HouseBlend.
*
*/
public HouseBlend() {
// TODO Auto-generated constructor stub
description = "HouseBlend";
}
@Override
Double cost() {
// TODO Auto-generated method stub
return .89;
}
}
class DarkRoast extends Beverage {
/**
* 创建一个新的实例 DarkRoast.
*
*/
public DarkRoast() {
// TODO Auto-generated constructor stub
description = "DarkRoast";
}
@Override
Double cost() {
// TODO Auto-generated method stub
return .99;
}
}
class Decaf extends Beverage {
/**
* 创建一个新的实例 Decaf.
*
*/
public Decaf() {
// TODO Auto-generated constructor stub
description = "Decaf";
}
public Decaf(Integer size) {
this.size = size;
description = "Decaf";
}
@Override
Double cost() {
// TODO Auto-generated method stub
return 1.05;
}
}
//接下来让调料进行实例化 其基类也是Beverage
class Mocha extends CondimentDecorator {
/**
* 创建一个新的实例 Mocha. 需要提供一个参数来附加到对应的饮料实体上
*
*/
public Mocha(Beverage beverage) {
// TODO Auto-generated constructor stub
superClassBeverage = beverage;
}
/**
* <p>Title: getDescription</p>
* <p>Description:之所以要重写getDescription 是因为对于调料而言 我们是要叠加上去的 所以还需要返回上级的描述!
* @return
* @see CondimentDecorator#getDescription()
*/
@Override
public String getDescription() {
// TODO Auto-generated method stub
return superClassBeverage.getDescription() + "Mocha";
}
/**
* <p>Title: cost</p>
* <p>Description: </p>
* @return
* @see Beverage#cost()
*/
@Override
Double cost() {
// TODO Auto-generated method stub
//这里增长size可以这样写
Double sizeCost = 0D;
if (superClassBeverage.getSize() == Beverage.BIG_SIZE) {
sizeCost += 0.20;
} else if (superClassBeverage.getSize() == Beverage.MEDIUM_SIZE) {
sizeCost += 0.15;
} else if (superClassBeverage.getSize() == Beverage.SMALL_SIZE) {
sizeCost += 0.10;
}
return sizeCost + superClassBeverage.cost() + .20;
}
}
class Milk extends CondimentDecorator {
/**
* 创建一个新的实例 Milk.
*
*/
public Milk(Beverage beverage) {
// TODO Auto-generated constructor stub
superClassBeverage = beverage;
}
@Override
public String getDescription() {
// TODO Auto-generated method stub
return superClassBeverage.description + "Milk";
}
@Override
Double cost() {
// TODO Auto-generated method stub
Double sizeCost = 0D;
if (superClassBeverage.getSize() == Beverage.BIG_SIZE) {
sizeCost += 0.20;
} else if (superClassBeverage.getSize() == Beverage.MEDIUM_SIZE) {
sizeCost += 0.15;
} else if (superClassBeverage.getSize() == Beverage.SMALL_SIZE) {
sizeCost += 0.10;
}
return sizeCost + superClassBeverage.cost() + .10;
}
}
class SoyaBean extends CondimentDecorator {
/**
* 创建一个新的实例 SoyaBean.
*
*/
public SoyaBean(Beverage beverage) {
// TODO Auto-generated constructor stub
superClassBeverage = beverage;
}
@Override
public String getDescription() {
// TODO Auto-generated method stub
return superClassBeverage + "SoyaBean";
}
@Override
Double cost() {
// TODO Auto-generated method stub
Double sizeCost = 0D;
if (superClassBeverage.getSize() == Beverage.BIG_SIZE) {
sizeCost += 0.20;
} else if (superClassBeverage.getSize() == Beverage.MEDIUM_SIZE) {
sizeCost += 0.15;
} else if (superClassBeverage.getSize() == Beverage.SMALL_SIZE) {
sizeCost += 0.10;
}
return sizeCost + superClassBeverage.cost() + .15;
}
}
class Whip extends CondimentDecorator {
/**
* 创建一个新的实例 Whip.
*
*/
public Whip(Beverage beverage) {
// TODO Auto-generated constructor stub
superClassBeverage = beverage;
}
@Override
public String getDescription() {
// TODO Auto-generated method stub
return superClassBeverage.getDescription() + "Whip";
}
/**
*
* <p>Title: cost</p>
* <p>Description: 以一种递归的方式来计算cost价格
* @return
* @see Beverage#cost()
*/
@Override
Double cost() {
// TODO Auto-generated method stub
return superClassBeverage.cost() + .10;
}
}
public class StarBuzzTest {
/**
* @Title: main
* @Description: TODO
* @param args
* @return void
* @throws
*/
public static void main(String[] args) {
//进行测试
System.out.print("不加配料的情况下:");
Beverage decafBeverage = new Decaf(Beverage.BIG_SIZE);//实例化一个decaf低咖啡因
System.out.println(decafBeverage.getDescription());//打印一下description
System.out.print("价钱:");
System.out.println(decafBeverage.cost());
//加上Milk后的描述和价钱
System.out.print("加Milk后的情况:");
CondimentDecorator decafWithMilk = new Milk(decafBeverage);
System.out.println( decafWithMilk.getDescription() );
System.out.print("价钱:");
System.out.printf("%.2f\n", decafWithMilk.cost());
//加Mocha后的情况
CondimentDecorator decafWithMilkAndMocha = new Mocha(decafWithMilk);
System.out.printf("再加上Mocha后的情形:");
System.out.println(decafWithMilkAndMocha.getDescription());
System.out.print("价钱:");
System.out.println(decafWithMilkAndMocha.cost());
}
}
/*不加配料的情况下:Decaf
价钱:1.05
加Milk后的情况:DecafMilk
价钱:1.15
再加上Mocha后的情形:DecafMilkMocha
价钱:1.35*/
工厂模式
使用工厂对象的示例
我们现在有如下的需求 我们需要一个披萨店订购不同的披萨 ** 披萨店家应该是只负责做披萨 而不需要关心它的种类该是啥 为了能动态的增加可以做的pizza类型 我们专门设定了一个pizza的工厂对象 这个工厂对象用来专门生产pizza 即返回对应的pizza实体** 这样可以使pizza店不会因为直接使用new而创造出具体的类出来 创建具体的类的工作由工厂来负责
/**
* @Title: PizzaFactoryTest.java
* @Package
* @Description: TODO(用一句话描述该文件做什么)
* @author Lustre
* @date 2019年12月9日
* @version V1.0
*/
/**
* @author Nigel
* @version 创建文件时间:2019年12月9日 上午11:33:27
*/
interface Pizza {
void prepare();
void cook();
void cut();
void box();//包装
}
//下面创建一些Pizza的实体类 从而才能在披萨工厂中创建对应的实体对象
class CheesePizza implements Pizza{
@Override
public void prepare() {
// TODO Auto-generated method stub
System.out.println("prepare " + this.getClass().getName());
}
@Override
public void cook() {
// TODO Auto-generated method stub
System.out.println("cook " + this.getClass().getName());
}
@Override
public void cut() {
// TODO Auto-generated method stub
System.out.println("cut CheesePizza");
}
@Override
public void box() {
// TODO Auto-generated method stub
System.out.println("box CheesePizza");
}
}
class PepperoniPizza implements Pizza {
@Override
public void prepare() {
// TODO Auto-generated method stub
}
@Override
public void cook() {
// TODO Auto-generated method stub
}
@Override
public void cut() {
// TODO Auto-generated method stub
}
@Override
public void box() {
// TODO Auto-generated method stub
}
}
class ClamPizza implements Pizza {
@Override
public void prepare() {
// TODO Auto-generated method stub
}
@Override
public void cook() {
// TODO Auto-generated method stub
}
@Override
public void cut() {
// TODO Auto-generated method stub
}
@Override
public void box() {
// TODO Auto-generated method stub
}
}
class VeggiePizza implements Pizza {
@Override
public void prepare() {
// TODO Auto-generated method stub
}
@Override
public void cook() {
// TODO Auto-generated method stub
}
@Override
public void cut() {
// TODO Auto-generated method stub
}
@Override
public void box() {
// TODO Auto-generated method stub
}
}
/**
*
* @ClassName: SimplePizzaFactory
* @Description: 只用来产出pizza种类的工厂类 专门负责对象的产生 这样我们可以重复利用产生不同对象的披萨对象(即该例中的变化)
* @author Nigel
* @date 2019年12月9日
*
*/
class SimplePizzaFactory {
public static final int CHEESE_PIZZA = 1;
public static final int PEPPERONI_PIZZA = 0;
public static final int CLAM_PIZZA = 2;
public static final int VEGGIE_PIZZA = 3;
/**
* @return
*
* @Title: createPizza
* @Description: 接收一个披萨的种类 用来创建不同的披萨饼 之所以是静态方法 是因为这样我们就可以不通过实例化方法产生pizza类!
* @param type
* @return void
* @throws
*/
public static Pizza createPizza(int type) {
Pizza pizza = null;
switch (type) {
case CHEESE_PIZZA:
pizza = new CheesePizza();
break;
case PEPPERONI_PIZZA:
pizza = new PepperoniPizza();
break;
case CLAM_PIZZA:
pizza = new ClamPizza();
break;
case VEGGIE_PIZZA:
pizza = new VeggiePizza();
break;
}
return pizza;//将创建好的pizza对象返回!
}
}
/**
* @ClassName: PizzaFactoryTest
* @Description: TODO(这里用一句话描述这个类的作用)
* @author Nigel
* @date 2019年12月9日
*
*/
public class PizzaFactoryTest {
/**
* @Title: main
* @Description: TODO
* @param args
* @return void
* @throws
*/
public static void main(String[] args) {
//这里实现pizza的配送 这里不再使用new运算符获得一个"具体的对象" 而是通过pizza工厂类的静态方法实现对pizza对象的获取
int myPizzaType = SimplePizzaFactory.CHEESE_PIZZA;
orderPizza(myPizzaType);
}
public static void orderPizza(int type) {
Pizza myPizza = SimplePizzaFactory.createPizza(type);
//然后委任任务给具体的pizza
myPizza.cook();
myPizza.cut();
myPizza.box();
}
}
使用工厂方法的示例
如果我们此时想要在不同的地区开区域连锁店 那么每个区域就应该要有不同的特色 此时如果我们依旧让工厂去生产 那么对于区域的局部性而言 其弹性就会不足 我们无法合理的进行扩展 因为披萨店是抽象的 我们无法应用具体的区域特色 例如披萨独特的口味 原料 等 此时我们可以使用工厂方法 即我们将之前的pizza店提取出来作为基类 并且让createPizza设定为抽象 但是制作流程保持一致 让对应的区域店来负责生产披萨的区域特色处理
示例代码如下
/**
* @Title: PizzaFactoryTest.java
* @Package
* @Description: TODO(用一句话描述该文件做什么)
* @author Lustre
* @date 2019年12月9日
* @version V1.0
*/
/**
* @author Nigel
* @version 创建文件时间:2019年12月9日 上午11:33:27
*/
abstract class Pizza {
public void prepare() {
// TODO Auto-generated method stub
System.out.println("prepare " + this.getClass().getName());
}
public void cook() {
// TODO Auto-generated method stub
System.out.println("cook " + this.getClass().getName());
}
public void cut() {
// TODO Auto-generated method stub
System.out.println("cut CheesePizza");
}
public void box() {
// TODO Auto-generated method stub
System.out.println("box CheesePizza");
}
}
//下面创建一些Pizza的实体类 从而才能在披萨工厂中创建对应的实体对象
class CheesePizza extends Pizza{
}
class PepperoniPizza extends Pizza {
}
class ClamPizza extends Pizza {
}
class VeggiePizza extends Pizza {
}
class NYStyleCheesePizza extends Pizza {
}
class NYStyleClamPizza extends Pizza {
}
class ChicagoStyleClamPizza extends Pizza {
}
class ChicagoStyleCheesePizza extends Pizza {
}
/**
*
* @ClassName: SimplePizzaFactory
* @Description: 只用来产出pizza种类的工厂类 专门负责对象的产生 这样我们可以重复利用产生不同对象的披萨对象(即该例中的变化)
* @author Nigel
* @date 2019年12月9日
*
*/
class SimplePizzaFactory {
public static final int CHEESE_PIZZA = 1;
public static final int PEPPERONI_PIZZA = 0;
public static final int CLAM_PIZZA = 2;
public static final int VEGGIE_PIZZA = 3;
/**
* @return
*
* @Title: createPizza
* @Description: 接收一个披萨的种类 用来创建不同的披萨饼 之所以是静态方法 是因为这样我们就可以不通过实例化方法产生pizza类!
* @param type
* @return void
* @throws
*/
public static Pizza createPizza(int type) {
Pizza pizza = null;
switch (type) {
case CHEESE_PIZZA:
pizza = new CheesePizza();
break;
case PEPPERONI_PIZZA:
pizza = new PepperoniPizza();
break;
case CLAM_PIZZA:
pizza = new ClamPizza();
break;
case VEGGIE_PIZZA:
pizza = new VeggiePizza();
break;
}
return pizza;//将创建好的pizza对象返回!
}
}
/**
*
* @ClassName: PizzaStore
* @Description: 此时将披萨店设置为基类 让区域店继承实现特色处理 同时也可以很好的处理创建具体对象的分隔问题
* @author Nigel
* @date 2019年12月9日
*
*/
abstract class PizzaStore {
public void orderPizza(int type) {
//这里我们仍然实现了抽象 披萨店仍然只创建pizza 因为点披萨的过程仍然是固定的
Pizza pizza = createPizza(type);
//下面仍然是委任
pizza.prepare();
pizza.cook();
pizza.cut();
pizza.box();
}
abstract public Pizza createPizza(int type);
}
class NYStyleCheesePizzaStore extends PizzaStore {
/**
*
* <p>Title: createPizza</p>
* <p>Description: 这里进行了重写createPizza方法
* @param type
* @return
* @see PizzaStore#createPizza(int)
*/
@Override
public Pizza createPizza(int type) {
// TODO Auto-generated method stub
Pizza pizza = null;
switch (type) {
case SimplePizzaFactory.CHEESE_PIZZA:
pizza = new NYStyleCheesePizza();
break;
case SimplePizzaFactory.PEPPERONI_PIZZA:
pizza = new PepperoniPizza();
break;
case SimplePizzaFactory.CLAM_PIZZA:
pizza = new NYStyleClamPizza();
break;
case SimplePizzaFactory.VEGGIE_PIZZA:
pizza = new VeggiePizza();
break;
}
return pizza;//将创建好的pizza对象返回!
}
}
class ChicagoStyleCheesePizzaStore extends PizzaStore {
/**
*
* <p>Title: createPizza</p>
* <p>Description: 这里进行了重写createPizza方法
* @param type
* @return
* @see PizzaStore#createPizza(int)
*/
@Override
public Pizza createPizza(int type) {
// TODO Auto-generated method stub
Pizza pizza = null;
switch (type) {
case SimplePizzaFactory.CHEESE_PIZZA:
pizza = new ChicagoStyleCheesePizza();
break;
case SimplePizzaFactory.PEPPERONI_PIZZA:
pizza = new PepperoniPizza();
break;
case SimplePizzaFactory.CLAM_PIZZA:
pizza = new ChicagoStyleClamPizza();//ChicagoStyleCheesePizza
break;
case SimplePizzaFactory.VEGGIE_PIZZA:
pizza = new VeggiePizza();
break;
}
return pizza;//将创建好的pizza对象返回!
}
}
/**
*
* @ClassName: NYStyleCheesePizza
* @Description: TODO(这里用一句话描述这个类的作用)
* @author Nigel
* @date 2019年12月9日
*
*/
/**
* @ClassName: PizzaFactoryTest
* @Description: TODO(这里用一句话描述这个类的作用)
* @author Nigel
* @date 2019年12月9日
*
*/
public class PizzaFactoryTest {
/**
* @Title: main
* @Description: TODO
* @param args
* @return void
* @throws
*/
public static void main(String[] args) {
//这里实现pizza的配送 这里不再使用new运算符获得一个"具体的对象" 而是通过pizza工厂类的静态方法实现对pizza对象的获取
System.out.println("点NY风格的两种披萨:");
NYStyleCheesePizzaStore storeOfNY = new NYStyleCheesePizzaStore();
storeOfNY.orderPizza(SimplePizzaFactory.CHEESE_PIZZA);
storeOfNY.orderPizza(SimplePizzaFactory.CLAM_PIZZA);
System.out.println("点Chicago风格的两种披萨:");
ChicagoStyleCheesePizzaStore storeOfChicago = new ChicagoStyleCheesePizzaStore();
storeOfChicago.orderPizza(SimplePizzaFactory.CHEESE_PIZZA);
storeOfChicago.orderPizza(SimplePizzaFactory.CLAM_PIZZA);
}
}
利用工厂对象实现原料分配(抽象工厂实现产品家族)
如果此时我们想在每个区域店的区域中开设我们自己的工厂 即我们想把生产原料的工作交给工厂对象来执行
利用抽象工厂 我们可以实现多个create的抽象 即多个对象的实例化
此时的示例代码如下(部分)
仅演示抽象工厂的创建部分
ructor stub
description = this.getClass().getName();
}
}
abstract class Cheese {
protected String description;
public String getDescription() {
return description;
}
}
class ReggianoCheese extends Cheese {
/**
* 创建一个新的实例 ReggianoCheese.
*
*/
public ReggianoCheese() {
// TODO Auto-generated constructor stub
description = this.getClass().getName();
}
}
abstract class Veggies {
protected String description;
public String getDescription() {
return description;
}
}
class Garlic extends Veggies{
/**
* 创建一个新的实例 BlackVeggies.
*
*/
public Garlic() {
// TODO Auto-generated constructor stub
description = this.getClass().getName();
}
}
class Onion extends Veggies{
/**
* 创建一个新的实例 BlackVeggies.
*
*/
public Onion() {
// TODO Auto-generated constructor stub
description = this.getClass().getName();
}
}
class Mushroom extends Veggies{
/**
* 创建一个新的实例 BlackVeggies.
*
*/
public Mushroom() {
// TODO Auto-generated constructor stub
description = this.getClass().getName();
}
}
/*
* 简单的披萨工厂接口
*/
interface PizzaIngredientFactory {
Dough createDough();
Sause createSauce();
Cheese createCheese();
Veggies[] createVeggies();
}
/**
*
* @ClassName: NYPizzaIngredientFactory
* @Description: 原料是具有地方特色的
* @author Nigel
* @date 2019年12月9日
*
*/
class NYPizzaIngredientFactory implements PizzaIngredientFactory {
@Override
public Dough createDough() {
// TODO Auto-generated method stub
return new ThinCrustDough();
}
@Override
public Sause createSauce() {
// TODO Auto-generated method stub
return new MarinaraSause();
}
@Override
public Cheese createCheese() {
// TODO Auto-generated method stub
return new ReggianoCheese();
}
@Override
public Veggies[] createVeggies() {
// TODO Auto-generated method stub
Veggies[] veggies = { new Garlic(), new Onion(), new Mushroom() };
return veggies;
}
}