不急着实现功能,先构思一下大概的功能,为了以后方便扩展和维护尽量使用好接口,继承,像我这样的新手菜鸟一般是,想到什么写什么,根本不考虑以后的扩展,一个文件写了几百行代码就感觉很有成就感,通过这个小项目,我要培养自己的架构能力,在此过程中遇到的问题我会一一记录下来和大家(新手)分享,共同学习探讨。
设计方案一:工厂方法
业务逻辑:利用简单工厂模式-->创建各个运算类的对象,各运算类继承自一个抽象基类,暴漏一个公共的接口。
先从简单开始吧。
我先在只是需要实现加减乘除四个功能,我完全可以将这四个功能单独写成各自的算法来实现,但是,如果我将来要为她添加求平方,平方根,平均数的运算时我该怎么办?如果真是这样我得对她进行“大手术”,要修改的代码量会很大,耦合度也很高,显然这样是并不合理的。那么我该选择怎样一个合理的方式呢?首先是一个 运算类,它有两个Number属性,主要用于计算器前后两个数的运算,然后有一个抽象方法getResult(),用于得到结果,然后我把加减乘除都写成了运算类的子类,继承父类后从写getResult()方法,这样的话在后期如果需要修改一个算法就需要提供其他算法代码了,但是我怎么让计算器知道我是希望用哪一个算法呢?这是我开始时遇到的问题,于是,我考虑用简单工厂模式,让工厂根据用户的需求选择合适的算法。
遇到的问题一:怎么让她易于扩展功能?
解决方案:抽象出运算基类,各功能继承该基类。
遇到的问题二:怎么让计算器知道我是希望用哪一个算法呢?
解决方案:用简单工厂模式,让工厂根据用户的需求选择合适的算法;
经过优化后(添加工厂方法):可以根据用户的需求创建运算类对象,用户只需选择运算符类型,即调用工厂方法的createOperate()方法。后面会贴出相应代码。
贴上上图代码及效果:
Operation:运算基类 该类为抽象类
public abstract class Operation {
//第一个操作数
private double firstNumber = 0d;
//第二个操作数
private double laseNumber = 0d;
//获取结果
public abstract double getResult();
public double getFirstNumber() {//取值
return this.firstNumber;
}
public double getLastNumber() {//取值
return this.laseNumber;
}
public void setFirstNumber(double firstNumber) {//赋值
this.firstNumber = firstNumber;
}
public void setLastNumber(double lastNumber) {//赋值
this.laseNumber = lastNumber;
}
}
OperationAdd:继承自Operation的加法运算类
public class OperationAdd extends Operation {
public double getResult() {
return getFirstNumber() + getLastNumber();
// TODO Auto-generated method stub
}
}
OperationMinus:继承自Operation的减法运算类
public class OperationMinus extends Operation{
public double getResult() {
// TODO Auto-generated method stub
return getFirstNumber()-getLastNumber();
}
}
OperationMutiply:继承自Operation的乘法运算类
public class OperationMutiply extends Operation{
public double getResult() {
// TODO Auto-generated method stub
return getFirstNumber()*getLastNumber();
}
}
OperationDevide:继承自Operation的除法运算类
public class OperationDevide extends Operation{
public double getResult() {
// TODO Auto-generated method stub
if(getLastNumber()!=0){
return getFirstNumber()/getLastNumber();
}
return 0.0;
}
}
OperationFactory:创建运算类对象的工厂类
public class OperationFactory {
private static Operation operation = null;
public static Operation createOperate(String operate) {
switch (operate) {
case "+":
operation = new OperationAdd();
break;
case "-":
operation = new OperationMinus();
break;
case "*":
operation = new OperationMutiply();
break;
case "/":
operation = new OperationDevide();
break;
default:
break;
}
return operation;
}
}
Test:
public class Test {
public static void main(String[] args) {
Operation operation = new OperationFactory().createOperate("*");
operation.setFirstNumber(5);
operation.setLastNumber(6);
double result = operation.getResult();
System.out.println("result = " + result);
}
}
结果:
先不考虑健壮性,单单从可扩展方面来说,以上就是我的初步想法之一。希望大家可以指出不足,共同探讨。
我会在今后的更新中继续优化,选择更合适的方法。