锁定老帖子 主题:OO design trap
该帖已经被评为精华帖
|
|
---|---|
作者 | 正文 |
发表时间:2005-12-26
规则引擎是面向对象的么?
|
|
返回顶楼 | |
发表时间:2005-12-26
buaawhl 写道 zengjin8310 写道 如果增加白金卡, 钻石卡, 铜卡, 铁卡, 铝卡
你还是要修改你的fill_type_stream , 如果用C++你的这种设计非常认同, 如果用java应该改进一把, 总归修改代码有点bed smell(虽然大多数情况下不可避免) T1 写道 为什么非要修改,添加不行么? 即使不改这些, 添加一个类, 肯定要改以前的某断调用代码 |
|
返回顶楼 | |
发表时间:2005-12-26
alin_ass 写道 规则引擎是面向对象的么?
这个问题问的好,但是如果从设计角度来探讨,实际上我们要问的应该是:能不能用OO设计方法来设计一个规则引擎?而不是探讨规则引擎本身是面向什么东西。 |
|
返回顶楼 | |
发表时间:2005-12-26
age0 写道 这种设计显然就是设计1的变种,只不过是将原来的Member拆成两部分,本质上依然是过程设计。OO的核心价值是封装、继承及多态,仅从封装角度来细分职责我认为是不足以体现OO价值的。
难道,你把使用member属性的所有操作都放入member中就能体现封装? 而“把稳定和变化的部分分离”,就不需要考虑? 正好俺正在研究Eclipse,其中有一个很重要的接口IAdaptable,它允许你通过扩展的方式,为对象添加行为。这无疑是“把稳定和变化部分分离”最佳示例。 |
|
返回顶楼 | |
发表时间:2005-12-26
partech 写道 这里假设,折扣只同member和order的信息有关,那么将来的任何变化,都可以只从getDiscount扩展出去。 这又是一个“概念依赖”的例子,好的DomainModel,就是职责划分合理的结构,而能打开这扇门的钥匙,我认为就是“概念依赖”。 同意partech的观点,不应该将什么东西都塞到Entity Object里面,应该做到责任分明。 我所知道有2种常见的处理可以解决这种用户可定制策略: 1. buaawhl给的CO 2. script,script如果做得完善的话,比如建立在CO上的script,就可以称之为DSL了(Domain Specific Language) 附件是用beanshell做的一个非常简单的script,来解决age0提出的情景。 |
|
返回顶楼 | |
发表时间:2005-12-26
buaawhl 写道 最后一个的 switch 最少,就选最后一个。
每次添加一个新的类型,所有hard coded switch的地方都需要修改。修改的地方,当然越少越好。最好就是只添加新类,不改动任何旧类代码。 一针见血。当然还可以用Spring之类的东西,继续减少hard code,转换成XML配置文件。 |
|
返回顶楼 | |
发表时间:2005-12-26
zengjin8310 写道 buaawhl 写道 zengjin8310 写道 如果增加白金卡, 钻石卡, 铜卡, 铁卡, 铝卡
你还是要修改你的fill_type_stream , 如果用C++你的这种设计非常认同, 如果用java应该改进一把, 总归修改代码有点bed smell(虽然大多数情况下不可避免) T1 写道 为什么非要修改,添加不行么? 即使不改这些, 添加一个类, 肯定要改以前的某断调用代码 T1给出了扩展例子。不需要修改以前的code。 T1的CO类似于,AOP的Interceptor的做法。只需要增加interceptor就可以了。 |
|
返回顶楼 | |
发表时间:2005-12-26
partech 写道 我所知道有2种常见的处理可以解决这种用户可定制策略: 1. buaawhl给的CO 2. script,script如果做得完善的话,比如建立在CO上的script,就可以称之为DSL了(Domain Specific Language) 附件是用beanshell做的一个非常简单的script,来解决age0提出的情景。 这个东西很不错啊,而且还是官方的,能做简单的规则引擎了 |
|
返回顶楼 | |
发表时间:2005-12-26
各位有兴趣提供解决方案的同志注意了,我们所面对的需求环境是极端恶劣的,你甚至可以认为超市boss是非常evil的,不要怀疑该boss会提出种各样让你诧异到想跳起来狠揍他但是从商业角度上考虑又合情合理的古怪需求,我们的忠告只有一个:prepare for everything。
评判设计优劣的标准主要有两个: 一是绝对的代码变更量,包括新增或修改的代码量,另外即使是修改xml之类的配置文件同样纳入变更范围,改代码和改配置并无本质区别。 二是变动所牵涉的范围:对原有代码的修改应该减至最少,尽可能逼近纯增量,修改所牵涉的类越少越好,并且应该避免引发接口变动。 就以OO设计二为例,如果需求仅仅是围绕member type发生变动,那么该设计无疑是符合要求的。只是不幸的是,后来的需求变动超出了设计的预估范围,以至画虎不成反成猫。 |
|
返回顶楼 | |
发表时间:2005-12-26
buaawhl 写道 zengjin8310 写道 buaawhl 写道 zengjin8310 写道 如果增加白金卡, 钻石卡, 铜卡, 铁卡, 铝卡
你还是要修改你的fill_type_stream , 如果用C++你的这种设计非常认同, 如果用java应该改进一把, 总归修改代码有点bed smell(虽然大多数情况下不可避免) T1 写道 为什么非要修改,添加不行么? 即使不改这些, 添加一个类, 肯定要改以前的某断调用代码 T1给出了扩展例子。不需要修改以前的code。 T1的CO类似于,AOP的Interceptor的做法。只需要增加interceptor就可以了。 Interceptor你要注册吧? 如果你都用代码总归注册的代码要改吧? 我说的改进就是用反射, or AOP把改动转移到配置文件 |
|
返回顶楼 | |