二、具体原则:
1. 单一职责原则 srp ( single responsibility principle )
一个模块的功能应该尽可能的内聚。如果一个类发生了变化,引起变化的原因应该有且只有一个。每一个类承担的职责都是一个变化的轴线,需求变化时,会体现为类的职责的变化。如果一个类承担的职责过多,就等于把这些职责耦合在了一起,一个职责的变化会影响这个类完成其他职责的能力,会出现前面所说的软件的臭味之一脆弱性。相关的设计模式有
2. 开放封闭原则 ocp ( open closed principle )
一个模块应该对功能的扩展开放,支持新的行为,对自身的更改封闭。每次对模块的修改都可能会引入新的错误和新的依赖。因此扩展新功能时,已经编好的模块源码和二进制代码都是不应该修改的。相关的设计模式有适配器模式,桥接模式,访问者模式等。
3. Liskov 替换原则 lsp ( liskov subtitle principle )
子类型必须可以替换掉他的基类型。一个基类的多个子类型之间要完成动态的替换,各个子类型必须都可以被他们的基类型替换,这样他们之间动态替换后,客户端调用的代码就不需要冗赘的 switch 类型判断代码。如果 子类型无法替换基类型,将会导致在派生类对象作为基类对象进行传值时的错误。这样多态机制处于瘫痪状态了。相关设计模式为组合模式。
4. 依赖倒置原则 dip ( dependent inverse principle )
高层模块不应该依赖于底层模块,抽象不应该依赖于细节,细节应该依赖于抽象。假定所有的具体类都是回变化的,因此如果一个客户端依赖于(调用或声明)具体的类型,那么当这个具体的类型变化时,依赖的客户端业必须同时进行修改。这些具体的更改可能出现在使用了某个特定的网络协议,特殊的系统 api 调用,特定的数据库储存过程等,这些用法或多或少都会使客户端调用和具体类型成为铁板一块,比较难于重用。 Java 社区中比较热门的 j2ee 轻量级容器框架 spring 就很好的实现了本原则。
5 .接口隔离原则 isp ( interface segregation principle )
不应该强迫客户依赖于它们不使用的方法。因为每一个实现接口的对象必须实现所有接口中定义的方法。如果接口的粒度比较小,实现接口的对象可以使用一种即用即付的方式动态实现接口。每个接口的粒度很小,复用起来也非常容易。
这体现了一个趋势:为了更好的实现重用,接口,函数,模块和类等倾向于更容易使用的“小”体积。
敏捷软件开发的宣言和实践:
软件开发项目的失败使得人们开始思考软件开发的过程,人们希望通过引入严格的过程控制产生软件生命周期中各个阶段的文档和制品来保证软件的质量。比较出名的业界实施方法论有 cmmi (能力成熟度模型)和 rup (瑞理统一过程),这些方法论都是重型的。
举例来说,没有经过剪裁的 Rup 实现起来,至少需要在全周期完成四十个以上的制品文档,文档的编写维护和源代码的同步等需要非常多的资源,十人以下的开发团队一般没有精力、时间、人员配置完成这些制品。失控的过程的膨胀迫使人们寻找一种快速工作,相应变化的“敏捷的”方法。敏捷团队提倡通过团队成员之间充分有效的沟通统一大家的目标,结伴的方式完成开发技术的团队内传承,使用“够用就好”的轻量甚至免费的工具管理过程。可以正常工作的代码摆在首要地位,只有必要的时候才生产必要的文档。强调和客户面对面地交流合作,积极地响应客户需求的变化而不是遵循机械的计划。
使用较短的迭代周期,近早和持续提交有价值的软件给客户来验证并修正和用户需求的吻合程度。提倡可以持续的稳定的开发节奏,长期“小步快走”的方式代替突然的“百米冲刺”。保持设计最优,最简单的设计并且持续改进,不断调整。