设计模式——工厂模式(基于《大话设计模式》)

简单工厂:

在这里插入图片描述
(emmm中文写名好像是有点不伦不类的)
产品类:

abstract class 方便面{
    private String 口味;
    abstract public void 查看信息();

    public 方便面(String 口味) {
        this.口味 = 口味;
    }

    public String get口味() {
        return 口味;
    }
} 

class 泡椒牛肉面 extends 方便面{

    public 泡椒牛肉面() {
        super("泡椒牛肉");
    }

    @Override
    public void 查看信息() {
        System.out.println("1号产品:"+get口味());   
    }
}

class 麻辣牛肉面 extends 方便面{

    public 麻辣牛肉面() {
        super("麻辣牛肉");
    }

    @Override
    public void 查看信息() {
        System.out.println("1号产品:"+get口味());
    }
}

简单工厂类

class 方便面简单工厂{
    public 方便面 生产方便面(String name){
        switch (name){
            case "泡椒牛肉面":
                return new 泡椒牛肉面();

            case "麻辣牛肉面":
                return new 麻辣牛肉面();

            default:
                throw new RuntimeException("没有这种面");

        }
    }
}

测试方法:

    @Test
    public void test(){
        方便面简单工厂 f = new 方便面简单工厂();
        try {
            方便面 ff = f.生产方便面("泡脚牛肉面");
        }catch (RuntimeException e){
            e.printStackTrace();
        }
        方便面 ff = f.生产方便面("泡椒牛肉面");
        ff.查看信息();
        ff = f.生产方便面("麻辣牛肉面");
        ff.查看信息();
    }

简单工厂模式,就像它的名字一样,简单,但是如果增添了其他类,就得修改工厂的代码,这不符合开放封闭原则。不过由于简单用得还是挺多的。

工厂方法:

这种模式可以形象的被称为工厂的工厂,一个工厂只负责一个产品的生产,如果另外还有产品需要生产,则创建新的工厂与产品联系起来。
在这里插入图片描述
这样就解决之前的问题啦
如果有新的产品出现,只需要再写个工厂就行了。
之前的产品类不用改动,工厂类写成:

interface I方便面工厂{
    方便面 生产方便面();
}

class 泡椒牛肉面工厂 implements I方便面工厂{

    @Override
    public 方便面 生产方便面() {
        return new 泡椒牛肉面();
    }
}

class 麻辣牛肉面工厂 implements I方便面工厂{

    @Override
    public 方便面 生产方便面() {
        return new 麻辣牛肉面();
    }
}

测试代码:

@Test
    public void test(){
        I方便面工厂 ifc = new 泡椒牛肉面工厂();
        方便面 f = ifc.生产方便面();
        f.查看信息();
        ifc = new 麻辣牛肉面工厂();
        f = ifc.生产方便面();
        f.查看信息();
    }

抽象工厂

在这里插入图片描述
抽象工厂是工厂方法的升级版,也就说多了多个产品族群,每一个工厂都不止生产一个产品而是生产一堆产品(或许叫产品群工厂方法更合适?)

抽象方便面类:

abstract class 火腿肠方便面{
    private String 口味;
    private final String 配菜 = "火腿肠";
    abstract public void 查看信息();

    public 火腿肠方便面(String 口味) {
        this.口味 = 口味;
    }

    public String get口味() {
        return 口味+配菜;
    }
} 

abstract class 鸭蛋方便面{
    private String 口味;
    private final String 配菜 = "鸭蛋";
    abstract public void 查看信息();

    public 鸭蛋方便面(String 口味) {
        this.口味 = 口味;
    }

    public String get口味() {
        return 口味+配菜;
    }
}

具体方便面类

class 火腿肠泡椒牛肉面 extends 火腿肠方便面{

    public 火腿肠泡椒牛肉面() {
        super("泡椒牛肉");
    }

    @Override
    public void 查看信息() {
        System.out.println("1号产品:"+get口味());   
    }
}

class 火腿肠麻辣牛肉面 extends 火腿肠方便面{

    public 火腿肠麻辣牛肉面() {
        super("麻辣牛肉");
    }

    @Override
    public void 查看信息() {
        System.out.println("2号产品:"+get口味());
    }
}

class 鸭蛋泡椒牛肉面 extends 鸭蛋方便面{

    public 鸭蛋泡椒牛肉面() {
        super("泡椒牛肉");
    }

    @Override
    public void 查看信息() {
        System.out.println("3号产品:"+get口味());
    }
}

class 鸭蛋麻辣牛肉面 extends 鸭蛋方便面{

    public 鸭蛋麻辣牛肉面() {
        super("麻辣牛肉");
    }

    @Override
    public void 查看信息() {
        System.out.println("4号产品:"+get口味());
    }
}

方便面工厂

interface I方便面工厂{
    火腿肠方便面 生产方便面加火腿肠();
    鸭蛋方便面 生产方便面加鸭蛋();
}

class 泡椒牛肉面工厂 implements I方便面工厂{


    @Override
    public 火腿肠方便面 生产方便面加火腿肠() {
        return new 火腿肠泡椒牛肉面();
    }

    @Override
    public 鸭蛋方便面 生产方便面加鸭蛋() {
        return new 鸭蛋泡椒牛肉面();
    }
}

class 麻辣牛肉面工厂 implements I方便面工厂{


    @Override
    public 火腿肠方便面 生产方便面加火腿肠() {
        return new 火腿肠麻辣牛肉面();
    }

    @Override
    public 鸭蛋方便面 生产方便面加鸭蛋() {
        return new 鸭蛋麻辣牛肉面();
    }
}

生产方便面工厂的工厂。

class 超级方便面工厂{
    private 超级方便面工厂(){}
    public static I方便面工厂 获取方便面工厂(String fac) throws ClassNotFoundException, NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {
        Class clazz = Class.forName(fac);
        return (I方便面工厂) clazz.getDeclaredConstructor().newInstance();
    }
}

测试代码:

public class Factoy {
    @Test
    public void test(){
        try {
            I方便面工厂  c = 超级方便面工厂.获取方便面工厂("泡椒牛肉面工厂");
            c.生产方便面加火腿肠().查看信息();
            c.生产方便面加鸭蛋().查看信息();
            c = 超级方便面工厂.获取方便面工厂("麻辣牛肉面工厂");
            c.生产方便面加火腿肠().查看信息();
            c.生产方便面加鸭蛋().查看信息();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        } catch (NoSuchMethodException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        } catch (InvocationTargetException e) {
            e.printStackTrace();
        } catch (InstantiationException e) {
            e.printStackTrace();
        }

    }
}

三种模式的比较:

如果业务相对简单,拓展性要求较低(如果使用反射也算是不违背开放封闭原则),那就可以使用简单工厂。代码量少
如果需要扩展且产品只有一类,则使用工厂方法。代码量较多
如果需要扩展且产品很很多类,则可使用抽象工厂。代码量贼多,极其复杂的业务才需要。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值