工厂模式

概述

定义一个用于创建对象的接口,让子类决定实例化哪一个类,

工厂模式的应用

Spring中通过getBean(“xxx”)获取Bean

为什么要使用工厂模式

创建对象的方式有很多种,可以通过new关键字,可以通过反射机制,可以通过clone()方式,那为什么还要使用工厂模式呢,new()在代码中最常用,可以他的灵活性太差了。
在这里插入图片描述
这段代码把对象的创建和使用放在一个类中,如果要进行修改引用类,换做另一个子类,那么必须修改loginAction的源代码,违反了开闭原则。最常用的解决方案就是把创建userdao对象的职责从loginAction类中移除,那么谁来创建userdao对象呢,答案是工厂类。
在这里插入图片描述
(1) 解耦 :把对象的创建和使用的过程分开
(2)降低代码重复: 如果创建某个对象的过程都很复杂,需要一定的代码量,而且很多地方都要用到,那么就会有很多的重复代码。
(3)降低维护成本 :由于创建过程都由工厂统一管理,所以发生业务逻辑变化,不需要找到所有需要创建对象B的地方去逐个修正,只需要在工厂里修改即可,降低维护成本。

1 简单工厂

简单工厂不是设计模式,他把实例化化的代码从应用代码中剥离,引入了创建者的概念,后续创建的实例如果需要改变,只需要改造创建这类即可。不能在运行期通过不同的方式去动态改变创建行为,因此存在一定的局限性,违反了我们的开闭原则,之主要靠循环语句实现。
角色分配:
1 工厂角色
2 抽象产品角色
3 具体产品角色

/**
 * @auther wkk
 * @date 2019/6/5 10:24
 */
public abstract class Coffee {
    /**
     * 获取coffee名称
     * @return
     */
    public abstract String getName();
}
/**
 * 美式咖啡
 * @author Lsj
 *
 */
 class Americano extends Coffee {
    @Override
    public String getName() {
        return "美式咖啡";
    }

}
/**
 * 卡布奇诺
 * @author Lsj
 *
 */
 class Cappuccino extends Coffee {

    @Override
    public String getName() {
        return "卡布奇诺";
    }

}

/**
 * 拿铁
 * @author Lsj
 *
 */
class Latte extends Coffee {

    @Override
    public String getName() {
        return "拿铁";
    }
}


class SimpleFactory {

    /**
     * 通过类型获取Coffee实例对象
     * @param type 咖啡类型
     * @return
     */
    public static Coffee createInstance(String type){
        if("americano".equals(type)){
            return new Americano();
        }else if("cappuccino".equals(type)){
            return new Cappuccino();
        }else if("latte".equals(type)){
            return new Latte();
        }else{
            throw new RuntimeException("type["+type+"]类型不可识别,没有匹配到可实例化的对象!");
        }
    }
    public static void main(String[] args) {
        Coffee latte = SimpleFactory.createInstance("latte");
        System.out.println("创建的咖啡实例为:" + latte.getName());
        Coffee cappuccino = SimpleFactory.createInstance("cappuccino");
        System.out.println("创建的咖啡实例为:" + cappuccino.getName());
    }

}

工厂模式

1.工厂方法模式应该是在工厂模式家族中是用的最多模式,一般项目中存在最多的就是这个模式,工厂方法模式是简单工厂的仅一步深化, 在工厂方法模式中,我们不再提供一个统一的工厂类来创建所有的对象,而是针对不同的对象提供不同的工厂。也就是说 每个对象都有一个与之对应的工厂类。

四个角色

1 抽象工厂
2 具体工厂
3 抽象产品
4 具体产品

使用场景

一个类不知道它所需要的对象的类:在工厂方法模式中,客户端不需要知道具体产品类的类名,只需要知道所对应的工厂即可,具体的产品对象由具体工厂类创建;客户端需要知道创建具体产品的工厂类。
我们来改良一下上面的案例

/**
 * 抽象工厂
 */
 interface Factory {
    public Coffee getCoffee();
}


class CappuccinoFactory implements Factory{

    @Override
    public Coffee getCoffee() {
        return new Cappuccino();
    }
}

class AmericanoFactory implements Factory{

    @Override
    public Coffee getCoffee() {
        return new Americano();
    }
}

class LatteFactory implements Factory{

    @Override
    public Coffee getCoffee() {
        return new Latte();
    }
}

class SimpleFactory {
    public static void main(String[] args) {
        Factory latteFactory=new LatteFactory();
        System.out.println(latteFactory.getCoffee().getName());
        Factory cappuccino=new CappuccinoFactory();
        System.out.println(cappuccino.getCoffee().getName());

    }

}

结果

拿铁
卡布奇诺

抽象工厂模式

在工厂方法模式中,其实我们有一个潜在意识的意识。那就是我们生产的都是同一类产品。抽象工厂模式是工厂方法的仅一步深化,在这个模式中的工厂类不单单可以创建一种产品,而是可以创建一组产品。

实例

interface Gun {
    public void shooting();
}
 interface Bullet {
    public void load();
}
//ak类产品
class AK implements Gun{

    @Override
    public void shooting() {
        System.out.println("shooting with AK");

    }

}

class AK_Bullet implements Bullet {

    @Override
    public void load() {
        System.out.println("Load bullets with AK");
    }

}
//M4A1类产品
class M4A1 implements Gun {

    @Override
    public void shooting() {
        System.out.println("shooting with M4A1");

    }

}
class M4A1_Bullet implements Bullet {

    @Override
    public void load() {
        System.out.println("Load bullets with M4A1");
    }
}

/**
 *抽象工厂
 */
 interface Factory {
    public Gun produceGun();
    public Bullet produceBullet();
}
//具体工厂  生产ak
 class AK_Factory implements Factory{

    @Override
    public Gun produceGun() {
        return new AK();
    }

    @Override
    public Bullet produceBullet() {
        return new AK_Bullet();
    }

}
//生产m4a1
class M4A1_Factory implements Factory{

    @Override
    public Gun produceGun() {
        return new M4A1();
    }

    @Override
    public Bullet produceBullet() {
        return new M4A1_Bullet();
    }

}
//测试
class Test {

    public static void main(String[] args) {

        Factory factory;
        Gun gun;
        Bullet bullet;

        factory =new AK_Factory();
        bullet=factory.produceBullet();
        bullet.load();
        gun=factory.produceGun();
        gun.shooting();

        factory =new M4A1_Factory();
        bullet=factory.produceBullet();
        bullet.load();
        gun=factory.produceGun();
        gun.shooting();
    }

}

参考 1 https://www.cnblogs.com/carryjack/p/7709861.html
2 https://blog.csdn.net/qq_34337272/article/details/80472071
3 https://blog.csdn.net/lovelion/article/details/7523392

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值