锁定老帖子 主题:对于OCP原则的困惑
该帖已经被评为精华帖
|
|
---|---|
作者 | 正文 |
发表时间:2004-09-23
ajoo 写道 其实,印证一下我那篇关于接口编程的公理游戏, 需求者用接口就可以ask no more。 服务者用接口就可以promise no more。 你的所谓公理:需求者用接口ask no more,服务者用接口promise no more。 大家可能看不大明白,我就用比较容易理解的方式翻译一下:接口定义要恰到好处。 这种公理大家可以随手拈来,并保证永远正确无误,举例:接口定义越恰当就越接近完美。 |
|
返回顶楼 | |
发表时间:2004-09-23
firebody 写道 ajoo
I 服了 you 不过仔细看了你的辩驳,嘿嘿,我甘败下风。 跟你吵架,无异于找death。 以后,一见到你ajoo远远冲过来,我立马退避三舍。哈哈 然后他就会撞在一块豆腐上。 |
|
返回顶楼 | |
发表时间:2004-09-23
to:ajoo
我可还没服,只是今天有点忙,明天再回帖。 |
|
返回顶楼 | |
发表时间:2004-09-23
我谈点看法吧:
1、OCP原则并非天生就有的,是代码进化的结果 2、实现OCP是以Interface为基础的,这里的Interface并非java的 interface,而是你组件的界面。 3、设计组件并非一开始就直奔OCP的,而是曲折近似的达到OCP。也就是这个Interface是进化的结果,也是Open的基础 4、有了Interface,你就可以有不同的实现,这就是close的表现 5、OCP并非着重是否修改代码,而是着重你对原有环境的影响,这里分2: A、一个未在运行的系统,如何让改动代价最少 B、一个在运行的系统,如何让改动不影响现有系统的运行。这也是OCP所关注的。 6、并非OO才能实现OCP |
|
返回顶楼 | |
发表时间:2004-09-23
我觉得这种问题讨论的甚是无趣。就像<Remains of the Day> 里面那个Stevens,拿着尺子测量杆盘刀叉与餐桌距离。
|
|
返回顶楼 | |
发表时间:2004-09-23
age0 写道 ajoo 写道 其实,印证一下我那篇关于接口编程的公理游戏, 需求者用接口就可以ask no more。 服务者用接口就可以promise no more。 你的所谓公理:需求者用接口ask no more,服务者用接口promise no more。 大家可能看不大明白,我就用比较容易理解的方式翻译一下:接口定义要恰到好处。 这种公理大家可以随手拈来,并保证永远正确无误,举例:接口定义越恰当就越接近完美。 随手拈来?照你这么说,ocp也可以说随手拈来,ioc我也是随手拈来的。都是很直觉化的东东。 两条平行线不相交你是否也觉得随手拈来? 正确无误不一定能够作为组成一个系统的基石,不一定具有实际操作性。 不知道你能否针对这两点给出反驳? 要不你随手拈来一个,我给你找毛病也行。 所谓“接口越恰当”如何如何,你要是拿来做公理,就有问题。 首先,接口的定义为何?是指interface吗? 其次,什么叫“恰当”? 你这句话的正确性仅仅建立在它的模糊性上,跟算命的差不多。这么主观性的形容词你也敢拿出来做公理? |
|
返回顶楼 | |
发表时间:2004-09-24
yhc0125 写道 我对OCP原则的困惑:
ocp原则的基本思想是对于扩展是开放的,对于更改是封闭的。该原则在java中的实现是通过接口完成的,可是在具体操作中功能的扩展是一定会出现变化的,这样怎么是对更改是封闭的呢? 比如说我定义了一个接口Interface A,他的一个实现class B,我在调用B来完成功能时这样做A temp = new B(); 这样的话当我给他另外一个实现class C时,我的客户段代码还是要改变的: A temp = new C(); 这也不是封闭的呀? 以上是我的理解,请各位指教小弟一下 首先明确一点,并不是使用interface就一定可以实现ocp的,而且使用interface和达到ocp没有什么必然的联系。 就像你的例子,比如我写成这样: public interface A { } public class B implements A { } public class Client { public void someMethod(); { A a = new B();; } } 好,对someMehtod的而言,这并不是ocp的,因为当需要把B换成C的时候,代码仍然需要修改。那么怎么办?做一个小变化。public void someMethod(); { A a = getA();; } private A getA(); { return new B();; } |
|
返回顶楼 | |
发表时间:2004-09-24
age0 写道 只要使用了继承,出现了派生类,OCP原则都会被打破,无论你如何部署代码,显式创建派生类的代码都是无可避免的。
如果你一定要坚持OCP原则,首先必须坚持CARP原则,只有CARP原则成立的情况下才能达到OCP的效果。 不一定,最简单的一个例子 public abstract Example { private static String defaultImplClass = "xxxx"; public static Example getInstance(); { String implClass = System.getProperty("xxxxx");; try { return Class.forName(implClass);.newInstance();; } catch (Exception e); { return Class.forName(defaultImplClass);.newInstance();; } } } 异常处理不完整,主要说这个意思。 |
|
返回顶楼 | |
发表时间:2004-09-24
庄表伟 写道 为什么要隔离?
设计为什么就是“丑陋”的? 隔离、美丽,都要付出代价的,这些代价,究竟该不该付出,是需要考虑的。 庄,我觉得还是一句话,对变化封装,如果不变,或者变化的可能很小,封装、隔离就意义不大,这个封装、隔离就成为了负担。 |
|
返回顶楼 | |
发表时间:2004-09-24
raimundox:
A a = AFactory.getInstance(); 这就ocp了吗? 我看不见得。你直接依赖于AFactory这个具体类。 如果需求变化成:根据用户输入的不同,选择两个不同的A的实现类。你怎么办? 改成: if(...); A a = Afactory1.getInstance();; else A a = Afactory2.getInstance();; 吗? 静态工厂根本就不是对应ocp原则的。它的目标是向内的,是封装内部的实现细节。对外部,它还是一个具体的依赖,和new AFactory()区别不大。 |
|
返回顶楼 | |