• 重构—改善既有代码的设计10)—简化函数调用


    “interface”。容易被理解、使用的接口,是开发良好面向对象软件的关键

      良好的接口,只向用户展现必须展现的东西。如果一个接口暴露了过多的细节,需要将不必要暴露的东西隐藏起来,从而改进接口的质量

      所有数据都应该隐藏起来。

      所有可以隐藏的函数都应该被隐藏起来。hide method、remove setting method  

    修改函数名称。最简单、最重要。名称是程序写作者、阅读者交流的关键工具

      只要能理解一段程序的功能,就应该大胆使用rename method,将自己所知道的东西传达给他人

      在适当时机,修改变量名称、类名称

    函数参数:add parameter、remove parameter

      对象技术,可以保持参数列的简短

      preserve whole object:来自同一个对象的多个值被当作参数传递

      introduce parameter object:对象不存在,创建一个参数对象

      replace parameter with method:函数参数来自该函数可获取的一个对象=》避免传递参数

      replace parameter with explicit method:参数被用来在条件表达式中做选择依据

      parameter method:为数个相似函数添加参数,将它们合并到一起

    警告:

      并发编程往往需要使用较长的参数列,可以保证传递给函数的参数都是不可修改的。

        例如:内置对象、值对象一定是不可变的

        可以使用不可变对象取代这样的长参数列。但必须对此类重构保持谨慎

    separate query from modifier:明确地将“修改对象状态”的函数和“查询对象状态”的函数分开设计

    replace constructor with factory method:不需要知道搞糟函数要创建的对象属于哪个类

    encapsulate downcast:将向下转型封装隐藏起来,避免让用户做那种动作

    replace error code with exception:以错误代码表示程序异常

    replace exception with test:测试

    1.rename method:修改函数名

    问题:函数的名称未能揭示函数的用途

    解决:修改函数名称

    动机:

      提倡的编程风格:将复杂的处理过程分解成小函数

        做不好=》费尽周折,却弄不清楚这些小函数各自的用途

        解决关键:给函数起个好名字。准确表达它的用途(将函数上的注释变成函数名称)

      一个函数名称不能很好表达其用途,应该立即修改。

        代码首先是为人写的,其次才是为计算机而写。而人需要良好命名的函数

        起个好名称并不容易,需要经验。要想成为一个真正的编程高手,起名的水平至关重要,函数签名中的其他部分也同样重要

      如果重新安排参数顺序,能够提高代码的清晰度,大胆去做。可运用add parameter、remove parameter

    做法:

      检查函数签名:是否被超类、子类实现过。

        是:针对每份实现分别进行下列步骤

      声明一个新函数,将其命名为新名称。将旧函数的代码复制到新函数中,进行适当调整

      修改旧函数,让其调用新函数

      找出旧函数的所有引用点,改而调用新函数

      删除旧函数

        如果旧函数是该类public接口的一部分,可能无法安全地删除它。这种情况下,将其保留在原处,并标记为deprecated(不建议使用)

    注意:添加、去除某个参数,过程大致相同

    2.add parameter:添加参数

    问题:某个函数需要从调用端得到更多信息

    解决:为此函数添加一个对象参数,让该对象带进函数所需信息

    动机:

      必须修改一个函数,修改后的函数需要一些过去没有的信息=》需要给该函数添加一个参数

      不使用本重构的时机:除了添加参数外,还有其他的选择

        只要可能,其他选择都比添加参数要好:不会增加参数列的长度

        过长的参数列是bad smell:程序员很难记住这么多参数=》data clumps

        提问:

          1.能从已有参数中得到需要的信息?

          2.能通过某个函数提供所需信息?

          3.需要将这些信息用于何处?此函数是否应该属于用改该信息的哪个对象所有

          4.针对现有参数,加入新参数是否合适?是否可以使用intruduce parameter object

        并非绝对不要添加参数。但是,在添加参数之前必须要了解其他选项

    做法:类似add parameter、remove parameter

      检查函数签名是否被超类、子类实现过?是:针对每份分别实现下列步骤

      声明一个新函数。名称与原函数同,只是添加新参数;将旧函数的代码复制到新函数中

        如果需要添加的参数不止一个,将其一次性添加进去比较容易

      修改旧函数,令其调用新函数

        可以给参数提供任意值。一般会给对象参数提供null;给内置型参数提供一个明显非正常值;数值型参数,建议使用0以外的值,这样比较容易将其认出来

      找出旧函数的所有引用点,将其修改为对新函数的引用,删除旧函数

        如果旧函数是该类public接口的一部分,可能无法安全地删除它。这种情况下,将其保留在原处,并标记为deprecated(不建议使用)

    3.remove parameter:移除参数

    问题:函数本体不再需要某个参数

    解决:将该参数去除

    动机:

      可能经常添加参数,却往往不愿意去掉它们:无论如何,多余的参数不会引起任何问题,而且以后可能用得上

        恶魔的诱惑

        参数代表着函数所需的信息,不同的参数值有不同的意义。

        函数调用者必须为每一个参数操心该传什么东西进去。如果不去掉多余参数,就是让每一位用户多费一份心。很不划算,且“去除参数”是非常简单的一项重构

      多态函数,情况有所不同,不能去除原有函数:可能多态函数的另一份(或多份)实现会使用这个参数,此时就不能去除它。

      

          

      

  • 相关阅读:
    DOM-DOMTree-查找

    用sql语句操作数据库
    数据查询基础
    【案例】城市地址三级联动
    【案例】城市地址二级联动
    【案例】高仿百度注册页
    【案例】自由运动小球
    【案例】使用上下左右键控制元素的移动
    事件
  • 原文地址:https://www.cnblogs.com/panpanwelcome/p/7819693.html
Copyright © 2020-2023  润新知