大话设计模式

第8章 工厂方法模式

2020-03-19  本文已影响0人  小超_8b2f
简单工厂模式示意图

简单工厂模式

import lombok.Data;
@Data
public abstract class Operation {
    private double numberA;
    private double nubmerB;
    public abstract double getResult();
}
class OperationAdd extends Operation {//加法
    @Override
    public double getResult() {
        return getNumberA() + getNubmerB();
    }
}
class OperationSub extends Opration {//减法
    @Override
    public double getResult() {
        return getNumberA() - getNubmerB();
    }
}
class OperationMul extends Opration {//乘法
    @Override
    public double getResult() {
        return getNumberA() * getNubmerB();
    }
}
class OperationDiv extends Opration {//除法
    @Override
    public double getResult() {
        if(getNubmerB() == 0)
            throw new RuntimeException("除数不能为0");
        return getNumberA() / getNubmerB();
    }
}
/**简单工厂类*/
public class OprationFactory {
    public static Operation createOperation(String op) {
        Operation2 result = null;
        switch(op) {
            case "+" : result = new OperationAdd();break;
            case "-" : result = new OperationSub();break;
            case "*" : result = new OperationMul();break;
            case "/" : result = new OperationDiv();break;
            default: System.out.println("操作符不合法!");break;
        }
        return result;
    }
}
/**客户端调用*/
public class Test {
    public static void main(String[] args) {
      Operation2 op = null;
      op = OprationFactory.createOperation("+");
      op.setNumberA(10);
      op.setNubmerB(20);
      double result = op.getResult();
    }
}
简单工厂模式的优点:

工程类中包含了必要的判断逻辑,根据客户端的选择条件动态实例化类,对于客户端来说,去除了与具体产品的依赖。

简单工厂模式的弊端:

简单工厂模式的工厂类的创建对象方法,需要根据客户需求动态的增加case分支来实现对新业务类的拓展。修改了原有的类!相当于不但对外拓展开放了,对外修改也开放了,这违背了:开放-封闭原则(工厂类与分支耦合)


工厂方法模式(Factory Method):

把工厂类抽象出一个接口,这个接口只有一个方法:就是创建抽象产品的工厂方法。当我们增加一个求M的N次方的类的时候,就不需要更改原有的工厂类了,只需要增加此功能的运算类和相应的工厂类就可以了。

工厂方法模式示意图
/**工厂方法的抽象*/
public interface IFactory {
    Operation2 createOperation();
}

/**工厂方法各种实例对象*/
public class AddFactory implements IFactory {
    @Override
    public Operation2 createOperation() {
        return new OperationAdd();
    }
}

public class SubFactory implements IFactory {
    @Override
    public Operation2 createOperation() {
        return new OperationSub();
    }
}

public class MulFactory implements IFactory {
    @Override
    public Operation2 createOperation() {
        return new OperationMul();
    }
}

public class DivFactory implements IFactory {
    @Override
    public Operation2 createOperation() {
        return new OperationDiv();
    }
}

class Client{
    public static void main(String[] args) {
        //换算法客户端只需要修改此处,且额外这增加个Operation2接口的实现类
        IFactory opFactory = new AddFactory();
        Operation2 op = opFactory.createOperation();
        op.setNumberA(10.0);
        op.setNubmerB(20.0);
        System.out.println("运算结果是:" + op.getResult());
    }
}

  这样整个工厂和产品体系都没有修改的变化,这就完全符合了开放-封闭原则的精神。
  工厂方法模式实现时,客户端需要决定实例化哪一个工厂来实现运算类,选择判断的问题还是存在的,也就是说,工厂方法把简单工厂的内部判断逻辑转移到了客户端代码来进行,你想要加功能,本来是要改工厂类的,现在是修改客户端!

工厂方法模式的缺点

每增加一个产品,就需要增加一个产品的工厂类,增加了额外的工作量,类数量也可能会急剧膨胀。用反射解决。

上一篇下一篇

猜你喜欢

热点阅读