大话设计模式-第8章 雷锋依然在人间--工厂方法模式- 高飞网

第8章 雷锋依然在人间--工厂方法模式

2016-02-01 18:14:03.0

    简单工厂模式,将客户端与产品实现通过工厂解耦合了,如果想增加一种产品,即要增加一个产品的实现,还需要在工厂中加一个case选择一个产品对象实例化。增加一个产品实现本身没有问题,但要在修改工厂代码,就违背了开放-封闭原则,使不仅扩展对象开放,修改也对外开放了。简单工厂模式的最大特点就在于其中包含了必要的逻辑判断,根据客户端的选择条件动态实例化相关的类,对于客户端来说,去除了与具体产品的依赖。  

工厂方法模式(Factory Method),定义一个用于创建对象的接口,让子类决定实例化哪一个类。工厂方法使一个类的实例化延迟到其子类。  


存在的问题:
工厂方法模式实现时,客户端需要决定实例化哪一个工厂来实现运算类,选择判断问题还是存在,即工厂方法把简单的工厂的内部逻辑判断移到了客户端代码来进行,如果想加功能,本来是要改工厂的,而现在是修改客户端。
另个好处。
如果想创建三个相同的加法类,那么简单工厂模式需要这样写:
Operation oper = OperationFactory.createOperation(op); //决定哪种操作实现的地方
Operation oper2 = OperationFactory.createOperation(op);//决定哪种操作实现的地方
Operation oper3 = OperationFactory.createOperation(op);//决定哪种操作实现的地方
如果用工厂方法模式:
IFactory factory = new AddFactory();//决定哪种操作实现的地方
Operation oper = factory.createOperation();
Operation oper = factory.createOperation();
Operation oper = factory.createOperation();



/** 运算接口与实现类 **/
import java.io.*;
public abstract class Operation{
        private int num1;
        private int num2;

        public void setNum1(int num1){
                this.num1 = num1;
        }      
        public int getNum1(){
                return this.num1;
        }
        public void setNum2(int num2){
                this.num2 = num2;
        }
        public int getNum2(){
                return this.num2;
        }
        public abstract int getResult();
}

public class OperationAdd extends Operation{
        @Override
                public int getResult(){
                        return getNum1() + getNum2();
                }
}
public class OperationSub extends Operation{
        @Override
                public int getResult(){
                        return getNum1() - getNum2();
                }
}
public class OperationMul extends Operation{
        @Override
                public int getResult(){
                        return getNum1() * getNum2();
                }
}
public class OperationDiv extends Operation{
        @Override
                public int getResult(){
                        try{
                                if(getNum2()==0){
                                        throw new Exception("除数不能为0");
                                }
                                return getNum1() / getNum2();
                        }catch(Exception e){

                        }
                        return 0;
                }
}

/** 工厂方法 **/
public interface IFactory{
        public Operation createOperation();
}

public class AddFactory implements IFactory{
        public Operation createOperation(){
                return new OperationAdd();
        }
}
public class SubFactory implements IFactory{
        public Operation createOperation(){
                return new OperationSub();
        }
}
public class MulFactory implements IFactory{
        public Operation createOperation(){
                return new OperationMul();
        }
}
public class DivFactory implements IFactory{
        public Operation createOperation(){
                return new OperationDiv();
        }
}
/** 驱动方法 **/
import java.io.*;
public class App{
        public static void main(String[] args)throws IOException{
                System.out.print("输入第一个数字:");
                BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
                String strNum1 = br.readLine();
                System.out.print("输入第二个数字:");
                BufferedReader br2 = new BufferedReader(new InputStreamReader(System.in));
                String strNum2 = br2.readLine();
                String op ="+";

                int num1 = Integer.parseInt(strNum1);
                int num2 = Integer.parseInt(strNum2);
                IFactory factory = new AddFactory();
                Operation oper = factory.createOperation();
                oper.setNum1(num1);
                oper.setNum2(num2);
                int result = oper.getResult();
                System.out.println(num1+op+num2+"="+result);
        }
}