资讯专栏INFORMATION COLUMN

工厂模式(一)之抽象工厂模式

woshicixide / 2389人阅读

摘要:主要详解简单工厂模式到抽象工厂模式的演变。抽象工厂模式当一个类别的产品还有多个系列区分时,为了按系列生产商品,使用抽象工厂区分。

主要详解简单工厂模式到抽象工厂模式的演变。

简单工厂模式

即静态工厂模式
1.将对象的创建和使用分开;
2.将生产过程集中,便于集中管理;
3.当需要创建的对象类有变动时,就不用在所有new 的地方修改了,直接修改工厂类即可;

/**
 * 简单工厂模式 --- 静态工厂模式
 */
public class StaticFactory {
    public static final int TYPE_APPLE = 1;//苹果
    public static final int TYPE_ORANGE = 2;//桔子
    public static final int TYPE_BANANA = 3;//香蕉

    public static Fruit getFruit(int type){
        if(TYPE_APPLE == type){
            return new Apple();
        } else if(TYPE_ORANGE == type){
           return new Orange("Peter",80);
        } else if(TYPE_BANANA == type){
            return new Banana();
        }
        return null;
    }

    /**
     * 多方法工厂
     * @return
     */
    public static Fruit getFruitApple(){
        return new Apple();
    }

    public static Fruit getFruitOrange(){
        return new Orange("Peter",80);
    }

    public static Fruit getFruitBanana(){
        return new Banana();
    }


}

总的来说,简单工厂模式就是用一个专业类(工厂类)来负责一种产品(水果类)的对象创建

简单工厂模式不属于23种设计模式,是工厂模式的基础.

思考?若工厂生产的产品越来越多,静态工厂不断修改,方法扩展极为庞大,产品品种扩展不优雅.

1.不符合单一职责原则:一个类负责了各类水果的创建.

2.不符合开闭原则:扩展品种时,需要修改已有代码,修改工厂类.

工厂方法模式

为了解决静态工厂的问题,我们采用工厂方法模式

1.将静态工厂打散,每一个水果品类,对应一个水果品类工厂来生产。

2.当需要扩展水果品类时,对应扩展一个水果品种的工厂即可。

将工厂类抽象出一个接口,对象的创建方法延迟到工厂子类去实现.

/**
 * 工厂方法接口
 */
public interface FruitFactory {
    public Fruit getFruit();//摘水果指令
}

/**
 * 橘子工厂子类
 */
public class OrangeFactory implements FruitFactory{
    public Fruit getFruit(){
        return new Orange("Peter",80);
    }
}


 /**
 * 香蕉工厂子类
 */
public class BananaFactory implements FruitFactory{
    public Fruit getFruit(){
        return new Banana();
    }
}
/**
 * 苹果工厂子类
 */
public class AppleFactory implements FruitFactory{
    public Fruit getFruit(){
        return new Apple();
    }
}

 /**
 * 水果获取测试
 *
 */
public class FruitTest {

    private static FruitFactory fruitFactory;

    public static void main(String[] args) {
        getFruit();
    }

    /**
     * 获得水果
     */
    public static void getFruit(){
        //初始化苹果工厂
        fruitFactory = new AppleFactory();
        Fruit fruit = fruitFactory.getFruit();
        fruit.draw();

        //初始化香蕉工厂
        fruitFactory = new BananaFactory ();
        Fruit bananafruit = fruitFactory.getFruit();
        bananafruit.draw();
        //想要获取什么水果就实例化哪个工厂

    }
}


通过工厂方法模式,解决了单一职责和开闭原则问题。
需要具体的产品则初始化对应的工厂,在spring中经常是配置在配置文件中,

//然后注入进去,面向接口编程我们注入的是接口实现类在配置里
@Autowired
private FruitFactory fruitFactory;


为什么使用抽象工厂模式

业务慢慢发展,现在水果店品种增加,那我们按着工厂方法模式新增其他工厂实现类。

现在除了卖水果的服务还要提供额外服务,比如要包装好,同样的我们就新建一个包装工厂接口如下BagFactory负责打包。

/**
 * 工厂方法模式
 */
public interface BagFactory {
    public Bag getBag();//打包指令
}
/**
 * 负责香蕉的打包
 */
public class BananaBagFactory implements BagFactory{
    public Bag getBag(){
        return new BananaBag();
    }
}
/**
 * 负责苹果的打包
 */
public class AppleBagFactory implements BagFactory{
    public Bag getBag(){
        return new AppleBag();
    }
}


一个水果店的动作,就有从工厂获取水果,然后从工厂获取打包服务,如下:

/**
 * 水果店测试
 * Created by Peter on 10/8 008.
 */
public class FruitStoreTest {

    private static FruitFactory fruitFactory;
    private static BagFactory bagFactory;

    public static void main(String[] args) {
        pack();
    }

    /**
     * 邮寄打包
     */
    public static void pack(){
        //初始化苹果工厂
        fruitFactory = new AppleFactory();//猎取工厂不对应
        Fruit fruit = fruitFactory.getFruit();
        fruit.draw();

        //初始化苹果包装工厂
        bagFactory = new BananaBagFactory();
        Bag bag = bagFactory.getBag();

        bag.pack();

        //....邮寄业务
    }   

产品类图如下:

同样的,要是再加一个邮寄业务,我们也是同样的新增一个邮寄工厂。

问题? 在实际写代码的时候是否会发生这种问题: 即猎取工厂不对应

1.初始化苹果工厂获取苹果

2.初始化香蕉工厂来做包装业务

3.初始化别的邮寄工厂来做邮寄服务

抽象工厂模式

针对上面的问题就要用到我们的抽象工厂模式了。

抽象工厂模式:当一个类别的产品还有多个系列区分时,为了按系列生产商品,使用抽象工厂区分。
比如不同水果有不同包装规格,客户下单时,自动配出包装,

--生产苹果,配置纸箱包装

--生产香蕉时,配置竹萝包装

PS:保证客户端只使用同一个产品族中的对象(如下代码的AppleFactory,BananaFactory)。

/**
 * 抽象水果工厂
 */
public abstract class AbstractFactory {

    public abstract  Fruit getFruit();

    public abstract Bag getBag();

}


/**
 * 水果工厂
 */
public class AppleFactory extends AbstractFactory{

    @Override
    public Fruit getFruit() {
        return new Apple();
    }

    @Override
    public Bag getBag() {
        return new AppleBag();
    }
}

/**
 * 水果工厂
 */
public class BananaFactory extends AbstractFactory{

    @Override
    public Fruit getFruit() {
        return new Banana();
    }

    @Override
    public Bag getBag() {
        return new BananaBag();
    }
}

/**
 * 抽象工厂模式测试
 * 按订单发送货品给客户
 * Created by Peter on 10/8 008.
 */
public class OrderSendClient {
    public static void main(String[] args){
        sendFruit();
    }

    public static void sendFruit(){
        //初始化工厂
        AbstractFactory factory = new AppleFactory();//spring使用注入方式

        //得到水果
        Fruit fruit = factory.getFruit();
        fruit.draw();
        //得到包装
        Bag bag = factory.getBag();
        bag.pack();
        //以下物流运输业务。。。。

    }

}

抽象工厂模式类图

代码地址:https://github.com/lovemumu/F...

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/77719.html

相关文章

  • Spring框架我见()——工厂模式

    摘要:相对于工厂模式,抽象工厂模式生产的对象更加具体,也更加丰富,但相对编码也更加复杂。具体的抽象工厂模式的实现大家可以参考菜鸟教程。知道了工厂模式和抽象工厂模式的区别,请大家使用的时候应该根据具体的情况进行选择。 大家好,今天给大家分享一些Spring的学习心得,在讲Spring之前,先和大家分享Spring中核心的设计模式。 工厂模式 在聊概念之前我先问问大家:什么是工厂? 这个很简单,...

    venmos 评论0 收藏0
  • 优才公开课笔记:php设计模式 (二)工厂模式

    摘要:但本质是,简单工厂并未严格遵循设计模式的开闭原则,当需要增加新产品时也需要修改工厂代码。但是工厂方法则严格遵守开闭原则,模式只负责抽象工厂接口,具体工厂交给客户去扩展。 最近开展了三次设计模式的公开课,现在来总结一下设计模式在PHP中的应用,这是第二篇创建型模式之工厂模式。 设计模式的一般介绍在第一篇文章讲了,这里就不重复。 工厂模式 实现:定义一个用于创建对象的接口,让子类决定实...

    aisuhua 评论0 收藏0
  • 设计模式抽象工厂

    摘要:类图上面的这张图引用设计模式之禅关于抽象工厂的通用类图,说实话,我觉得这张图很难懂,不容易表述抽象工厂模式也或许是个人理解能力。 前言 关于抽象工厂模式,博主初学的时候是懵逼的,花了好大力气才明白它与工厂模式的异同,不得不说理解能力还有待加强(~。~) 什么是抽象工厂模式 为创建一组相关或相互依赖的对象提供一个接口,而且无须指定它们的具体类。 让我们再回顾下工厂模式的定义: 定义一个用...

    VincentFF 评论0 收藏0
  • 个设计模式JS实现——工厂模式

    摘要:参考文章深入理解三种工厂模式工厂模式,工厂方法模式,抽象工厂模式详解工厂模式是中最常用的设计模式之一。这种类型的设计模式属于创建型模式,它提供了一种创建对象的最佳方式。 参考文章:深入理解java三种工厂模式工厂模式,工厂方法模式,抽象工厂模式 详解 工厂模式(Factory Pattern)是 Java 中最常用的设计模式之一。这种类型的设计模式属于创建型模式,它提供了一种创建对象的...

    Muninn 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<