在过程式(procedural)软件中,无法彻底保证程序的正确性。仅举一个例子,只要代码中还存在没有被断言专门排除的副作用,断言就被绕过了。不管我们多么遵守模型驱动设计,最终还是要编写过程式的程序来生成概念交互的结果。我们花了很多时间编写样板代码,但这些代码实际上并不增加任何业务概念上的意义或行为。揭示意图的接口和本章中的其他模式虽然有所帮助,但它们永远不会给常规的面向对象编程带来形式化的严格性。
这些正是声明式设计背后的部分动机。声明式设计这一术语对不同的人有不同的含义,但通常指的是,把程序或程序的一部分写成一种可执行的规格说明(specification)的编程方式。在这种方式下,软件实际上是由一些非常精确的属性描述来控制的。可以通过多种方式来实现这一点。例如,可以使用反射机制,或者在编译时通过代码生成来完成(根据声明自动生成常规代码)。通过这种方法,其他开发人员从字面意义上就可以直接理解程序的声明。这给程序的正确性提供了严格的的保证。
对于很多声明式的方法,如果开发人员有意无意地绕过它们,那么这些方法就被破坏了。当用于声明式开发的系统很难使用或限制过多时,就可能发生这种情况。为了获得声明式编程的好处,每个人都应该遵守框架的规则。
声明式的设计风格
一旦设计中有了揭示意图的接口、无副作用函数和断言,就具有一定的声明式风格了。当我们有了可以组合在一起相互沟通其含义的元素,并且它们产生的作用都是表征化(characterized)或者说显式的,也就是说完全没有外部可观测的副作用,这时就可以获得声明性设计的许多好处了。
柔性设计可以使客户端代码使用声明式设计风格。为了说明这一点,下一节将综合使用本章中的一些模式,使规格模式(Specification)更加柔性,更具声明性。 【译者注:Specification(规格)模式在《DDD》原书的9.2.3节中介绍。但并没有包含在本参考手册中。上面这句话也是原书中的,不应该出现在本参考手册中。估计是作者编写本手册时,从原书中把这段话直接拷贝过来,忘记删去了。】