zoukankan      html  css  js  c++  java
  • 《大话设计模式》第四章

    对于扩展是开放的,对于更改是封闭的

    无论模块是多么的“封闭”,都会存在些无法对之封闭的变化。我们是很难预先猜测,但我们却可以在发生小变化时,就及早去想办法应对发生更大变化的问题。也就是说,等到变化发生时立即采取行动。正所谓,同一地方,摔第一跤不是你的错,再次在此摔跤就是你的不对了。

    在我们最初编写代码时,假设变化不会发生。当变化发生时,我们就创建抽象来隔离以后发生的同类变化。面对需求,对程序的改动是通过增加新代码进行的,而不是更改现有的代码。

    当然,并不是什么时候应对变化都是容易的,我们希望的是在开发工作展开不久就知道可能发生的变化。查明可能发生的变化所等待的时间越长,要创建正确的抽象就越困难。

    开发人员应该仅对程序中呈现出频繁变化的那些部分做出抽象,然而,对于应用程序中的每个部分都刻意地进行抽象同样不是一个好主意。拒绝不成熟的抽象和抽象本身一样重要。

    --高级的开发人员就是之前经历过变化,或事先就能预感到哪些是较大可能性的变化,

    从子程序到控件的发展,就是经历“对更改是封闭”的这个动作。原来,我们的操作逻辑都用子程序体现出来,但这些子程序一旦给其它程序员使用,他们在自己的程序出错时,就跟踪到了子程序里面,然后想当然地以为共用的子程序出错了(准确地,可以说外部的条件不满足子程序的要求,也可以说子程序的功能不够强),然后就开始更改子程序,后面就越改越乱。后来,我们把这些子程序封装到控件中去,这些程序员根本无法调试进入这些代码,因此更不要说更改代码了。
    虽然说我们解决了一部分问题,但随之而来的问题是程序员出错后,根本不知道是什么原因出错,然后只能提交给公司的核心技术人员来调试,如果中间沟通的不够充分,核心技术人员又无法创建相应的出错情况,那处理时间又被拖延。开放代码与不开放代码中间,我们无从决择。开放代码造成公司关键技术到处流传,也不是个好事。假设我们决定“坚决不开放代码”……不过即使其它公司,也没有非常好的解决方案,这也离题了。
    控件这一些是“对更改是封闭”的实现了,但“对扩展是开放”的,实现得不那么好,我们虽然在控件中有插入事件,如BeforeClick、AfterClick,但要想象类那样创建新对象,自由地或完全地替代对象的某个方法是不可能的,虽然有时完全替代一个复杂的逻辑也不是个好主意,但类的继承仍然能够随时调用父类的原来处理过程,这就有极大的灵活性。
    有时说,VB的控件完全没有“对扩展是开放”,这明显也是错的,如果我们创建一个控件,然后控件中拉入别人写得很好的控件时,自己再加上一两个功能,也是实现了把别人控件的好东西都带来,而自己又加上了一些功能。只是这种复用是功能上的复用,而不是代码上的复用。

    我要用什么实例来体现出类的“对更改是封闭的,对扩展是开放的”这一点呢?

    什么是更改,什么是扩展,如果猜数字的游戏中,我原来只能猜3位的数,现在要“扩展”为猜4位的数,能够通过不修改原来的类代码就扩展吗?显然不行。
    这是否是说,类的扩展也是有限的,它还与当初设计类的人的能力有关,一个糟糕的类,在变化面前,对其只能进行更改,而不是扩展。
    更深的课题应该是“如何设计出良好的类?”,让别人有较多的扩展空间。

    这一次,我试着新建一个“类库”的项目,里面加入game.cs这个类,并且,让这个类写得像话一点,并且在设计时,考虑有可能扩展为几位。
    对错误的修改,例如输入的位数不够的判断,还是必须进入类而进行修改。
    对功能性的扩展,如,要想加入一个最后提示你成功,或再加上你成功的步数。好象不行。

    我这个类糟糕得实在不行了。

  • 相关阅读:
    Java 第十一届 蓝桥杯 省模拟赛 洁净数
    Java 第十一届 蓝桥杯 省模拟赛 第十层的二叉树
    Java 第十一届 蓝桥杯 省模拟赛 第十层的二叉树
    Java 第十一届 蓝桥杯 省模拟赛 第十层的二叉树
    Java 第十一届 蓝桥杯 省模拟赛 70044与113148的最大公约数
    Java 第十一届 蓝桥杯 省模拟赛 70044与113148的最大公约数
    20. Valid Parentheses
    290. Word Pattern
    205. Isomorphic Strings
    71. Simplify Path
  • 原文地址:https://www.cnblogs.com/yzx99/p/1243778.html
Copyright © 2011-2022 走看看