美文网首页
【设计模式】简单工厂模式之实现一个简单计算器

【设计模式】简单工厂模式之实现一个简单计算器

作者: flowerAO | 来源:发表于2018-04-24 22:40 被阅读0次

    要求

    实现一个简单计算器

    思路

    Iter1 初始草稿

    #!/usr/bin/python
    #coding:utf-8
    
    
    if __name__ == "__main__":
        A = raw_input("请输入数字A: ")
        B = raw_input("请输入运算符号(+、-、*、/): ")
        C = raw_input("请输入数字B: ")
        if B == "+":
            D = float(A) + float(C)
        if B == "-":
            D = float(A) - float(C)
        if B == "*":
            D = float(A) * float(C)
        if B == "/":
            D = float(A) / float(C)
        print "结果是: ", D
    
    问题:
    • 命名不规范
    • 异常判断
    • 判断分支多次做无用功

    Iter2 进一步规范化

    #!/usr/bin/python
    #coding:utf-8
    
    
    if __name__ == "__main__":
        try:
            strNumberA = raw_input("请输入数字A: ")
            strOperate = raw_input("请输入运算符号(+、-、*、/): ")
            strNumberB = raw_input("请输入数字B: ")
            swithcer = {
                "+": float(strNumberA) + float(strNumberB),
                "-": float(strNumberA) - float(strNumberB),
                "*": float(strNumberA) * float(strNumberB),
                "/": float(strNumberA) / float(strNumberB)
            }
    
            D = swithcer[strOperate]
            print "结果是: ", D
        except Exception, e:
            print "结果有错: ", e
    
    问题:
    • 达不到高质量代码的要求
      • 不易维护
      • 不易扩展
      • 不易复用

    即完成之后是否还有被利用的价值

    Iter3 封装业务

    #!/usr/bin/python
    # coding:utf-8
    
    
    class Operation:
        def __init__(self, numberA, numberB):
            self.numberA = numberA
            self.numberB = numberB
    
        def getresult(self, operate):
            swithcer = {
                "+": float(self.numberA) + float(self.numberB),
                "-": float(self.numberA) - float(self.numberB),
                "*": float(self.numberA) * float(self.numberB),
                "/": float(self.numberA) / float(self.numberB)
            }
            return swithcer[operate]
    
    
    if __name__ == "__main__":
        try:
            strNumberA = raw_input("请输入数字A: ")
            strOperate = raw_input("请输入运算符号(+、-、*、/): ")
            strNumberB = raw_input("请输入数字B: ")
            D = Operation(strNumberA, strNumberB).getresult(strOperate)
            print "结果是: ", D
        except Exception, e:
            print "结果有错: ", e
    
    
    问题:
    • 耦合太高
      • 若要增加一个运算,却需要其他的运算都来参加编译
      • 安全性,对于原有的代码有风险

    Iter4 松耦合

    #!/usr/bin/python
    # coding:utf-8
    
    
    class Operation:
        def __init__(self, numberA, numberB):
            self.numberA = numberA
            self.numberB = numberB
    
    # 父类需不需要有getresult(self)方法,为什么?
    
    class OperationAdd(Operation):
        def getresult(self):
            return float(self.numberA) + float(self.numberB)
    
    
    class OperationSub(Operation):
        def getresult(self):
            return float(self.numberA) - float(self.numberB)
    
    
    class OperationMul(Operation):
        def getresult(self):
            return float(self.numberA) * float(self.numberB)
    
    
    class OperationDiv(Operation):
        def getresult(self):
            return float(self.numberA) / float(self.numberB)
    
    

    以上松耦合,修改任何一个算法,不需要提供其他算法的代码

    问题:
    • 实例化问题(如何知道调用哪个运算方法?)

    Iter5 简单工厂模式

    用一个单独的类来选择调用,即工厂。

    #!/usr/bin/python
    # coding:utf-8
    
    
    class OperationFactory:
        @staticmethod
        def createOperate(operate):
            switcher = {
                "+": OperationAdd(),
                "-": OperationSub(),
                "*": OperationMul(),
                "/": OperationDiv()
            }
            return switcher[operate]
    
    
    class Operation:
        numberA = 0
        numberB = 0
    
        def getresult(self):
            return 0
    
    
    class OperationAdd(Operation):
        def getresult(self):
            return float(self.numberA) + float(self.numberB)
    
    
    class OperationSub(Operation):
        def getresult(self):
            return float(self.numberA) - float(self.numberB)
    
    
    class OperationMul(Operation):
        def getresult(self):
            return float(self.numberA) * float(self.numberB)
    
    
    class OperationDiv(Operation):
        def getresult(self):
            return float(self.numberA) / float(self.numberB)
    
    
    if __name__ == "__main__":
        try:
            strNumberA = raw_input("请输入数字A: ")
            strOperate = raw_input("请输入运算符号(+、-、*、/): ")
            strNumberB = raw_input("请输入数字B: ")
    
            oper = OperationFactory.createOperate(strOperate)
            oper.numberA = float(strNumberA)
            oper.numberB = float(strNumberB)
            D = oper.getresult()
            print "结果是: ", D
        except Exception, e:
            print "结果有错: ", e
    
    
    

    这样一来,只需要输入运算符号,工厂就实例化出合适的对象。通过多台,返回父类的方式实现了计算器的结果。
    任何程序都可以通过调用工厂来实现计算器的功能。

    UML图

    SimpleFactory

    细碎python

    • @staticmethod 用途及用法

    • 异常捕获机制

    • python 子类父类调用关系

    • raw_input() 与 input() 区别
      • python3.x中仅有input(),将一切输入视作字符串
      • python2.x中
    in\out raw_input() input()
    str str str(需加引号)
    int str int
    bool str bool
    表达式 str 结果值

    Ps

    果然写下来一目了然,写下来才能理解。
    用3个小时整理输出,其中很多涉及到Python的细碎的知识也需要花时间整理。
    在设计模式之后,还有算法、网络编程、数据库等知识,需要浸入。
    平静是本事,持续平静是习惯。
    已经4月底,夏天要来了。

    相关文章

      网友评论

          本文标题:【设计模式】简单工厂模式之实现一个简单计算器

          本文链接:https://www.haomeiwen.com/subject/ukqrlftx.html