简单工厂模式、工厂方法模式、抽象工厂模式演变之JAVA实战理解和图解

发布于:2022-11-28 ⋅ 阅读:(332) ⋅ 点赞:(0)

目录

其他设计模式和设计原则

一、简单工厂设计模式

二、工厂方法设计模式

三、抽象方法设计模式

总结


其他设计模式和设计原则

七大设计原则实战图解
建造者设计模式实战图解

一、简单工厂设计模式

相关概念:
        1、产品:类
        2、抽象产品:抽象类、接口
        3、产品簇:多个有内在联系,或者有逻辑关系的抽象产品。
        4、产品等级:一个抽象产品,多个产品实现该抽象产品,这个整体称之为一个产品等级

图解产品簇和产品等级:

优点:
        1、把具体产品的类型,从客户端代码中,解耦出来
        2、服务器端,如果修改了具体的产品类名,客户端不知道也不需要知道!
         这便符合了”面向接口编程“的思想,也符合了迪米特法则(最少知道原则)
            
缺点:

        1、客户端不得不死记硬背那些常量和具体产品的映射关系
        2、如果具体产品特别多,则简单工厂就会变得十分的臃肿,比如有1000个具体产品,则需要
        在简单工厂的switch中写100个case
        3、最重要的是变化来了,客户端需要扩展具体产品的时候,势必要修改简单工厂中的代码,
        这便违反了”开闭原则“

interface Food{//抽象产品
    void eat();
}

class Hamburger implements Food{//具体产品1
    @Override
    public void eat() {
        System.out.println("吃汉堡包!");
    }
}

class Rice implements Food{//具体产品2
    @Override
    public void eat() {
        System.out.println("吃大米!");
    }
}

class FoodFactory{//产品工厂
    public static Food getFood(int n){
        Food food = null;
        switch (n) {
            case 1:
                food = new Hamburger();
                break;
            case 2:
                food = new Rice();
                break;
        }
        return food;
    }
}

public class AppTest {//客户端
    public static void main(String[] args) {
        Food food = FoodFactory.getFood(1);
        food.eat();
    }
}

 UML图解:为上述例子作出图解

二、工厂方法设计模式

优点:
        1、仍然具有简单工厂的优点,服务器端修改了具体产品的类名以后,

        客户端不知道也不需要知道
        2、当客户端需要扩展一个新的产品时,不需要修改作者原来的代码,

        只是扩展一个新的工厂而已
杠点:
        1、我们已经知道,简单工厂也好,工厂方法也好,都有一个优点,

        就是服务器端的具体产品类名变化了以后,客户端不知道也不需要知道!
        但是,反观我们现在的代码,客户端仍然依赖于具体的工厂的类名呀!此时如果服务端修改

        了具体工厂的类名,那么客户端也要随之一起修改,感觉折腾了一圈,又回到了原点!!!
        解释:
                工厂的名字,是视为接口的,作者有责任,有义务,保证工厂的名字是稳定的。也就是

                说,虽然客户端依赖于工厂的具体类名,可是在IT业内 ,所有工厂的名字都是趋向于稳

                定 (并不是100%不变),至少工厂类的名字,要比具体产品类的名字更加稳定
        2、既然产品是我们自己客户端扩展出来的,那为什么不直接自己实例化呢?毕竟扩展出来的

        这个产品,我们自己就是作者,我们想怎么改类名自己都能把控,为什么还要为自己制作的

        产品做工厂来实例化呢?
        解释:
                因为,作者在开发功能时,不仅仅只会开发一些抽象产品、具体产品、对应的工厂,还

                会配套的搭配一些提前做好的框架。
    
缺点:
        如果有多个产品等级(食物产品等级、饮料产品等级等等),那么工厂类的数量就会爆

        炸式增长

interface Food{//抽象产品
    void eat();
}

class Hamburger implements Food{//具体产品1
    @Override
    public void eat() {
        System.out.println("吃汉堡包!");
    }
}

class Rice implements Food{//具体产品2
    @Override
    public void eat() {
        System.out.println("吃大米!");
    }
}

interface FoodFactory{//工厂
    Food getFood();
}

class HamburgerFactory implements FoodFactory{
    @Override
    public Food getFood() {
        return new Hamburger();
    }
}

class RiceFactory implements FoodFactory{
    @Override
    public Food getFood() {
        return new Rice();
    }
}

//-------------------------------------如果扩展一个产品Noodle
class Noodle implements Food{//具体产品3
    @Override
    public void eat() {
        System.out.println("吃面条!");
    }
}
class NoodleFactory implements FoodFactory{
    @Override
    public Food getFood() {
        return new Noodle();
    }
}
public class AppTest {//客户端
    public static void main(String[] args) {
        //FoodFactory foodFactory = new HamburgerFactory();
        //FoodFactory riceFactory = new RiceFactory();
        FoodFactory noodleFactory = new NoodleFactory();
        Food food = noodleFactory.getFood();
        food.eat();
    }
}

UML图解:为上述例子作出图解

三、抽象方法设计模式

优点:
        1、仍然有简单工厂和工厂方法的优点
        2、更重要的是,抽象工厂把工厂类的数量减少了!无论有多少个产品等级,工厂就一套
        
缺点:

        1、当产品等级发生变化时(增加或删除产品等级),都要引起所有以前工厂代码的修改,这

        就违反了“开闭原则”

interface Food{//抽象产品
    void eat();
}

class Hamburger implements Food{//具体产品1
    @Override
    public void eat() {
        System.out.println("吃汉堡包!");
    }
}

class Rice implements Food{//具体产品2
    @Override
    public void eat() {
        System.out.println("吃大米!");
    }
}

interface Drink{//抽象产品
    void drink();
}

class Cole implements Drink{//具体产品1
    @Override
    public void drink() {
        System.out.println("喝可口可乐!");
    }
}

class Meizhiyuan implements Drink{//具体产品2
    @Override
    public void drink() {
        System.out.println("无添加剂美汁源,值得一喝!");
    }
}

interface Factory{//抽象工厂
    Food getFood();
    Drink getDrink();
}

class KFCFactory implements Factory{//KFC工厂
    @Override
    public Food getFood() {
        return new Hamburger();
    }

    @Override
    public Drink getDrink() {
        return new Cole();
    }
}

class MacDonaldFactory implements Factory{//麦当劳工厂
    @Override
    public Food getFood() {
        return new Rice();
    }

    @Override
    public Drink getDrink() {
        return new Meizhiyuan();
    }
}

class Bussiness{//中间商品尝
    public static void taste(Factory factory) {
        System.out.println("商业评委品尝:");
        factory.getDrink().drink();
        factory.getFood().eat();
    }
}

public class AppTest {//用户选择品尝哪家店
    public static void main(String[] args) {
        //品尝KFC
        Bussiness.taste(new KFCFactory());
        //品尝麦当劳
        //Bussiness.taste(new MacDonaldFactory());
    }
}

 UML图解:为上述例子作出图解


总结

当产品等级比较固定的,可以考虑使用抽象工厂模式。
当产品等级经常变化时,则不建议使用抽象工厂模式,可以考虑使用工厂方法设计模式。
当产品少且固定变化少时,简单工厂设计模式即可。。

-----结束语:以感恩的心去开启每天的生活,带给周边的人你幸福,也珍惜自己平静的幸福,大概这就是在这急躁社会中寻找的人生意义吧!!!

本文含有隐藏内容,请 开通VIP 后查看

网站公告

今日签到

点亮在社区的每一天
去签到