`
lonelybug
  • 浏览: 11995 次
  • 性别: Icon_minigender_1
文章分类
社区版块
存档分类
最新评论

解释一下,为什么需要接口而不直接实现类。

阅读更多
看了这里的一些帖子和很多地方的帖子,很多人都在问为什么非要interface或者abstract class,然后还要在写一个实现类,而其实,我就市要做一个很简单的功能!?

对,如果你制作一个简单的功能,我同意你可以直接使用spring hibernate等框架来写,他们本身的好处也是干这个的。

但是,中国人有句老话,叫做杞人忧天,很多的时候,你有没有内心问自己,这个系统,我设计的,如果老板要改动,我可以在很短的时间内做到改变么?

当你问自己这个问题的时候,你就已经把直接写实现类的做法怀疑了。

面向接口的原则,不是只出现在程序员或者说IT界,接口设计是人类对一个问题或者一个物体的概括理解能力的表现。我们日常生活中处处有接口。

在我作一个简单的说明之前,我要补充以下,系统框架中,除了层的概念,还有一个叫做boundary,每一个layer(层)是由不同的boundary(box)组成。

举例一二三,比如,简单的说,发电厂就是实现类(implementation class),每个发电厂都是独立的boundary,而发电厂就是统称为一个layer,也许还不明白,比如,我们平时说,发电厂,没人关心你家的电来自于那个发电厂,而关心的是你家的插座有没有电,所以三项插座,二项插座至十发电厂给用户的最终接口。发电厂之间也是通过一个特殊的工业接口来互相访问,所以,这也是为什么说,有时候有的发电厂在夏天负担过重,就可以把负担分给其他的电场供应。反过来,如果让老百姓天天关心的是发电厂,而不是插座,那你觉得这样的城市电力设计是不是很糟糕呢?

在举个例子,比如果.....,嗯,好,就说汽车,汽车都见过吧,四个轮子,一个方向盘,但是,你们有没有发现,有时候你们的汽车上面的音响系统坏掉或者要升级的时候,只需要取下中间面板上面的那个独立的音响播放器,然后买一个新的,由汽车维修给你们撞上就可以了,不管是飞利浦,boss还是简单的radio的和卡带的,你们从来不会在买一个汽车音响的时候关心他能不能安在汽车上,而是可以完全关心颜色,款式,品牌这些问题上,如果,反过来设计,每一个汽车品牌都直接实现自己的独立设计,不遵循工业接口,那你觉得这样的汽车音响会有很多选择么?

最后在举一个我们每天息息相关的例子,门,每天人们通过不同的门,进入或者走出不同的地方,而门就是那个地方或者建筑物的接口,如果说,我们反过来,每个大厦或者建筑物都直接应用自己喜欢的实现进出的方式,那你们觉得每天的生活会不会有点太麻烦?

我举例子只是来简单的解释一下,接口不是一个繁琐的过程,而是每个工业,甚至是每天生活中,我们必须应用到的东西,所以,如果看待现在的文明社会用程序员的方式的话,那么就是一种接口世界,现实生活中很多人叫做标准或者协议,由看得见摸得找的,也有看不见摸不着的接口。

很多人可能想对我举的例子进行进一步的反驳,其实没有必要,如果你要跟我探讨每一个例子来映射程序中的接口问题,那就是在抬杠,抬杠很浪费时间,所以,我不会跟你探讨例子的问题,那就是个例子,而这个例子是每天确实发生的,使用的。

希望能解释明白一点在程序设计中接口编程的优势所在。
分享到:
评论
61 楼 robbin 2008-10-07  
axeon 写道
在最开始我就已经说了,用比较文明的话说,这是学院派和实战派的意识形态上的争议。

新特性必须要有需求支撑的,而且是实际存在的有力需求,否则这个新特性是屠龙术,只存在于口舌之中的快感。

ioc/di是不是替代性的技术,解决了什么问题,付出代价是否值得,这个现在都有很大的争议,而不是单纯是spring的争议问题。如果仅仅是一种基于改良的技术方案,那么就要看还有没有其他的办法。解决一个问题要看成本,实现同样的需求,你会选择一个更复杂的办法么?而且这个办法可能还会带来其他的问题。

另外,有一点比较搞笑的是,有几个tx在站内短消息里面支持我,还有人加了我的qq,而他们在帖子里面表示的更偏向中立一些,这姑且算是中庸之道吧。



对于稍微有点规模的应用来说,IoC容器当然可以减轻很多程序员手工维护对象依赖的工作量,而且在系统的可维护性、可测试性方面有更多的可以看到的好处。这也是为什么在Java世界里面IoC容器这么流行的主要原因。开源框架并没有厂商的推动,如果不是实实在在的解决了很多问题,根本不可能流行开来。具体到Spring来说,的确太臃肿了一些,所以很多人开始抛弃Spring。比方说Google的Adwords就是用Guice来做IoC容器的。

当然你非要说IoC是没有价值,没有你的静态方法好用,那你就一直用静态方法也挺好,越是原始的方法,越容易被掌握,越不容易出问题。

至于说Java开发软件过于臃肿,过于烦琐,原罪并不在所谓的SSH开源框架上,还是在于Java本身的语法和API上,以及非常糟糕的Servlet/JSP规范制定上,当然现在主流的开源框架不够简洁也在推波助澜。但抛弃先进的框架,寻求原生的API和JSP编程,并不能够从根本上解决开发效率和可维护性问题。
60 楼 axeon 2008-10-07  
robbin,我觉得有一点很有意思。
当年你和jdon的板桥辩论的时候,可否想到今天也有人和你在这里辩论?
你的辩论到现在也不能彻底影响jdon上板桥的支持者!
jdon的拥护者至今也会认为他们才代表真正的企业级开发,呵呵!


不过,从现在来看,你表现的要比板桥高明一些,呵呵。
59 楼 yuan 2008-10-07  
terranhao 写道

有点头大,能不能再具体一些?
比如能用直接的一个例子来说明好处吗?
为什么要消除工厂?工厂不是面向接口编程的一个很好的实践吗,四巨头的书不也是提倡工厂吗?
我一直就是搞不清spring的最好的地方在哪里,自己想也没想明白。IOC到底好在哪里?
谢谢指教。

学spring那阵收藏的一个帖子:http://www.iteye.com/topic/3067估计能帮上你。
58 楼 axeon 2008-10-07  
robbin 写道
引用
一、企业应用软件市场本来仅仅是一个市场分类而已,仅此而已,这个市场本来在这里已经认定是java的市场了,还有什么意义?但是软件市场不仅仅是一个企业应用软件市场。

二、作为了一个古老的java程序员,我一直在不停的观察和研究最新的技术,不过这几年让我非常失望,java目前的发展方向绝对是一条歧路,违背了技术发展的规律。歧路的根本在于习惯了使用复杂和繁琐的办法去解决并不复杂的问题。

三、所谓的ioc,di已经成了spring的代名词,这个技术本身现在仍然有很大争议。di/ioc的价值和意义我认为还是不明确的,他缺乏一个有力需求的支撑,作为个人观点,我持有否定态度。但是这仍然是一种技术选择,优劣自然由市场来判断。

四、对于实现业务逻辑,单例和静态方法毫无区别,因为都意味着这是一个无状态的类。但是使用spring来达到这个目的,远远比直接使用语言特性来实现要愚蠢的多。使用某种技术仅仅是一种实现结果的过程而已,只要能更好更有效的实现,自然会选择更简便的办法。

五、至于资历,并无摆的意思,只是因为有些人看着眼扎的慌,呵呵。


一、你应该这样反思一下,为什么PHP/Perl无法进入企业应用软件市场?

二、面向接口编程和使用IoC容器正是Java回归面向对象本质的正确道路。

三、Java的IoC容器多的很,Pico,Google Guice,Hivemind等等,恐怕是你视线过于狭隘了。

四、简单来说,就是你还是面向过程的编程思路,不是面向对象的编程思路。当然,我承认对于很多场合,面向过程的方式的确简单而有效,所以在你而言,面向过程才是正确的路,面向对象是愚蠢的。


一、php/perl不能进入企业开发市场原因很简单,他们太低调了。缺乏java提出的庞大的,令人眼花缭乱的框架,更缺乏忽悠的概念,诸如enterprise的说辞,ejb,soa,云计算等等听起来心潮澎湃的词语。

二、是不是正确道路从来不是靠人说出的,而是靠实践证明的,无数正确道路最后都没能走下去。

三、java的容器很多,不但但ioc的,osgi的也很多,看看谁比谁说的更有价值。

四、我说了,我是实战派的,因为我在不停的做项目,做应用,这或许是我的短板,因为做的太多了,反而不敢说。
57 楼 terranhao 2008-10-07  
robbin 写道
terranhao 写道
其实我也想了解下spring带来的真正的好处。
比如我IUserDAO dao=new UserDAO();
用spring 就是IUserDAO dao=beanFactory.getBean("userDAO");

假如以后我想把IUserDAO换成另外一种实现
IUserDAO dao=new UserDAO2();
对应spring: IUserDAO dao=beanFactory.getBean("userDAO2");

也许有人会说,我直接在spring的配置文件中将ID为userDAO的类的type改为UserDAO2就可以了,程序不用改动。但这又有什么太重大的优点呢?我用IDE的refactor一样可以马上将new UserDAO()换成new UserDAO2();

请问好处是什么?谁能告诉我?


其实像你这样用spring,等于spring根本没有入门。 Spring作为一个IoC的价值就在于消除工厂,结果你把Spring当成了一个大工厂来用。在Spring的思路来说,接口的意义在于:你不需要关心userDao是怎么来的,你可以直接拿到userDao。

有点头大,能不能再具体一些?
比如能用直接的一个例子来说明好处吗?
为什么要消除工厂?工厂不是面向接口编程的一个很好的实践吗,四巨头的书不也是提倡工厂吗?
我一直就是搞不清spring的最好的地方在哪里,自己想也没想明白。IOC到底好在哪里?
谢谢指教。
56 楼 axeon 2008-10-07  
在最开始我就已经说了,用比较文明的话说,这是学院派和实战派的意识形态上的争议。

新特性必须要有需求支撑的,而且是实际存在的有力需求,否则这个新特性是屠龙术,只存在于口舌之中的快感。

ioc/di是不是替代性的技术,解决了什么问题,付出代价是否值得,这个现在都有很大的争议,而不是单纯是spring的争议问题。如果仅仅是一种基于改良的技术方案,那么就要看还有没有其他的办法。解决一个问题要看成本,实现同样的需求,你会选择一个更复杂的办法么?而且这个办法可能还会带来其他的问题。

另外,有一点比较搞笑的是,有几个tx在站内短消息里面支持我,还有人加了我的qq,而他们在帖子里面表示的更偏向中立一些,这姑且算是中庸之道吧。
55 楼 fuliang 2008-10-07  
接口的目的一:多态,如果需要新的实现,只需要增加一个实现就可以满足,满足了开闭原则;二、在于依赖倒置,依赖于抽象而不是具体,如果没有接口和抽象类,那么系统的抽象程度就不够,没法去依赖倒置。依赖倒置作为面向对象的一个重要原则,抽象的东西总是不容易变的,所以要依赖抽象而不是具体的类,这也是分离变化并封装之的体现。
54 楼 robbin 2008-10-07  
引用
一、企业应用软件市场本来仅仅是一个市场分类而已,仅此而已,这个市场本来在这里已经认定是java的市场了,还有什么意义?但是软件市场不仅仅是一个企业应用软件市场。

二、作为了一个古老的java程序员,我一直在不停的观察和研究最新的技术,不过这几年让我非常失望,java目前的发展方向绝对是一条歧路,违背了技术发展的规律。歧路的根本在于习惯了使用复杂和繁琐的办法去解决并不复杂的问题。

三、所谓的ioc,di已经成了spring的代名词,这个技术本身现在仍然有很大争议。di/ioc的价值和意义我认为还是不明确的,他缺乏一个有力需求的支撑,作为个人观点,我持有否定态度。但是这仍然是一种技术选择,优劣自然由市场来判断。

四、对于实现业务逻辑,单例和静态方法毫无区别,因为都意味着这是一个无状态的类。但是使用spring来达到这个目的,远远比直接使用语言特性来实现要愚蠢的多。使用某种技术仅仅是一种实现结果的过程而已,只要能更好更有效的实现,自然会选择更简便的办法。

五、至于资历,并无摆的意思,只是因为有些人看着眼扎的慌,呵呵。


一、你应该这样反思一下,为什么PHP/Perl无法进入企业应用软件市场?

二、面向接口编程和使用IoC容器正是Java回归面向对象本质的正确道路。

三、Java的IoC容器多的很,Pico,Google Guice,Hivemind等等,恐怕是你视线过于狭隘了。

四、简单来说,就是你还是面向过程的编程思路,不是面向对象的编程思路。当然,我承认对于很多场合,面向过程的方式的确简单而有效,所以在你而言,面向过程才是正确的路,面向对象是愚蠢的。
53 楼 robbin 2008-10-07  
我其实也比较诧异怎么2008年还会有这样的讨论,印象当中这种讨论只应该出现在03年或者04年。

这个讨论实际上掺杂了两个话题:一个是Java为什么要面向接口编程;另一个是Java为什么要IoC。


一、Java为什么要面向接口编程?

Java借鉴了C++的语法,但是为了简化,Java不支持C++的多继承。我们知道,对象有时候会同时具备多个不同的特征,在不同的应用场合,我们只关注该对象某一个特征,而不关心它其他方面的特征:比方说我这个人就具备多种特征:在网络上面是一个知名ID,在家里是妻子的老公;在公司是别人的同事;在父母面前是儿子等等。为了表达这种抽象特征面,Java引入了接口的概念(实际上也是借鉴了C++的虚函数)。在其他面向对象语言比方说Ruby,尽管ruby也不支持多继承,但是ruby有module和duck typing,可以更灵活的表达对象多种不同特征,因此Ruby不需要接口。从Java的编程实践来说,如果预期对象不具备多种不同的特征的话,就没有必要使用接口。从这个意义上来说,如果DAO的实现不会切换的话,确实没有必要搞DAO接口出来。

二、Java为什么要IoC?

依赖注入,而不是手工创建依赖关系对象,是大型应用程序分离关注点,实现对象的单一职责,降低模块藕合性的内在要求,或者简单的说就是面向对象的软件设计要求你进行“依赖注入(DI)”,而不是用静态方法自己手工创建依赖关系。从这一点上来说,Spring作为一个IoC容器是不够纯粹的,因为Spring会绑定一些依赖关系,而且暴露了beanFactory,间接鼓励你使用工厂创建依赖,所以Spring一直以来都有不少的争议。很多人会选择更加纯粹的Pico或者Google Guice。

自从Java流行IoC容器以来,确实推动了面向接口编程的风气,因为良好的面向接口编程才能方便的进行IoC。但反过来看,没有IoC容器,也并不意味着你不应该面向接口编程,只要对象能够抽象出来不同的特征面,就应该面向接口编程。这实际上是面向对象对于对象单一职责、降低藕合性的要求。
52 楼 axeon 2008-10-07  
robbin 写道
axeon 写道
也许大家都不觉得这是个问题,为什么呢?有的人认为用接口是理所当然的,无需置疑的,有的人,比如我,就觉得这根本就是多余。

从观点上,这是学院派和实战派的区别,这是好听的话。

为什么出现这种现象,我想还是技术背景的问题。

第一个是时间界限:凡是02以后做java的,普遍都能接受类似struts,spring,hibernate之类的框架,02年之前做java的,接受并且使用这些框架是有些困难的。这是一个先入为主的问题,上来就用所谓ssh这些框架,哪里有时间和机会来思考和质疑呢?
第二个是语言界限:语言背景越是单一的,特别是只做过java的,越是对ssh深信不疑,以致崇拜。语言背景越是复杂的,比如做过c,delphi,php,.net,ruby的,越容易对ssh产生怀疑感。

任何一门技术,从最基础的经济学角度来说,都要满足多快好省的要求,才能不被淘汰,才能够淘汰别人。那么什么是多块好省呢?我的理解是要能够快速开发,运行还要高效。如果从这个观点来评判,我想思路会更加清晰的。

新技术的特性必然要有需求与此对应,否则这个新特性就是屠龙术,仅仅有可吹嘘的本钱。另外,这个需求首先应该是业务需求,而不是解决自身问题的。因为技术最终是为业务服务的,通过业务来体现技术价值。

首先肯定一点,JAVA本身并没有错,它仅仅是一门语言而已。

和同时期,早期一些,晚期一些的语言相比,java现在成绩如何呢?我想可以通过sourceforge上的开源项目数量来评判。如果从项目数量来看,我想php>perl>java吧?没准过几年ruby超越java也不是不可能。

有人说java的市场在企业级开发上,点点市面上的产品,又有多少家是抱着ssh开发的呢?

java这几年的失败,一方面是sun的问题,一方面也许就是定位所谓的企业级,还有一方面就是社团的注意力过多的关注在所谓的架构上,而不是产品应用上。

从多快好省的角度上来说,java当前所谓框架的代表ssh,引导的是一个开发慢,运行慢的技术派系,他的所谓维护性和扩展性(或许)优势是不明确的,甚至是不存在的。开发效率和运行效率是最大的软肋。

为什么会有“忽悠”,就是因为偷懒,不经大脑思考,就就跟风呼叫的人太多了,这误导了下一批人,因为众口铄金,皇帝的新衣面前,还有几人敢于说话?

技术浪潮总是几年来一次,大浪淘沙。有人站在最前面得利了,但是最傻的是后面跟着抬轿子的。所有的技术革新,你必须有先知先觉。

javaeye是怎么起来的?是因为ejb,一直到现在还有为ejb呼喊的jdon,当然,这个jdon还被好多人笑话过呢。我想当年ejb火的时候,你们肯定也像义和团一样保卫ejb。因为有的人压根就不用脑子思考,搞不清自己的站位,就连吵架,也是看哪边人多,就站在哪边的。

当然spring确实解决了一些问题,包括从版本发展的过程中也有所进化,甚至做了不少自我否定。跟着spring屁股后面否定自己,甚至有口难言的,我想都不在少数!

为什么要接口?除了隐藏实现,那么就是多态。如果使用spring,有什么好隐藏的?更因为编译器就绑定实现了,怎么玩多态?如果为了庞大而好看,我建议你一个类里只写一个方法好了!

为什么要继承?而不用调用?相比较继承,调用是更清晰的关系,除非是必要继承,没事儿你继承什么?

更不说大把人用的spring的beanFactory,更是笑死人了!这也是spring对他来说最重要的用处。首先如果只用单例,我干嘛不在类和方法上加上static?从实际使用上来说,spring通过hashmap来查找实例,而static是从内存直接调用,哪个更简单,效率更好,甚至零配置?

至于分层,更是笑话!曾经有一个帖子,抱怨招聘了一个技术高手,过来之后就会分层。结果招致群攻,简直笑死我了。我回了一个帖子,说了一句按需分层,竟然被评差贴。

一个项目的技术水平根本就不可以用是否使用ssh,是否分层来进行判断。更不说大把分层的代码里面仅仅是对上层的调用,但是如果程序需要改动,分层越多越难改,便于维护压根就是一个说辞。


从开始做java到现在,已经9年了。做的项目,有国家级的大项目,也有每日访问量500w的互联网项目,总结经验,ssh和项目质量,产品性能压根无关,也和项目维护更无关。倒是常见一些用ssh做互联网项目做的非常失败的,表现在开发速度慢,运行速度慢,系统运维难度大。

如果更公正的说,ssh可能适合一些小型的企业应用项目,除此,ssh和ssh倡导的一些理念丝毫排不上用场。




一、你拿Java和PHP/Perl比较是不公平的,一个是编译语言,一个是脚本语言。其实在企业应用软件市场,没有PHP/Perl的份。

二、你对SSH开源框架的蔑视也多少说明了一个拥有9年经验的古老的Java程序员对新技术(尽管SSH已经不新)与生俱来,发自内心的抵制,而且事实上你对Spring作为一个IoC容器的价值是没有领会到的。

三、尽管你口口声声抵制接口,但实际上你想抵制的真正目标并不是接口而是Spring,这体现在你一直声称应该用静态方法,而不是IoC容器上面。

四、不要过多摆资历,从某种意义上来说,摆资历是露怯的表现。



一、企业应用软件市场本来仅仅是一个市场分类而已,仅此而已,这个市场本来在这里已经认定是java的市场了,还有什么意义?但是软件市场不仅仅是一个企业应用软件市场。

二、作为了一个古老的java程序员,我一直在不停的观察和研究最新的技术,不过这几年让我非常失望,java目前的发展方向绝对是一条歧路,违背了技术发展的规律。歧路的根本在于习惯了使用复杂和繁琐的办法去解决并不复杂的问题。

三、所谓的ioc,di已经成了spring的代名词,这个技术本身现在仍然有很大争议。di/ioc的价值和意义我认为还是不明确的,他缺乏一个有力需求的支撑,作为个人观点,我持有否定态度。但是这仍然是一种技术选择,优劣自然由市场来判断。

四、对于实现业务逻辑,单例和静态方法毫无区别,因为都意味着这是一个无状态的类。但是使用spring来达到这个目的,远远比直接使用语言特性来实现要愚蠢的多。使用某种技术仅仅是一种实现结果的过程而已,只要能更好更有效的实现,自然会选择更简便的办法。

五、至于资历,并无摆的意思,只是因为有些人看着眼扎的慌,呵呵。
51 楼 neodoxy 2008-10-07  
面对对象用不好,比面对过程还意大利面,类的继承是高耦合的,在一个需求不断变化的环境里,滥用继承带来的维护难度远远大于他的开发成本,而且还具有危险性,现在的面对对象语言并未提供对父类的过期方法的屏蔽,唯一能做的就是覆盖,但这不是能够忍受的事情吧?所以面对接口的编程,乃至委托这种概念,比继承更干净,也更面对对象
50 楼 bloodrate 2008-10-07  
spring是个大杂烩,企图把能集成的流行开发思想都集成近来,IOC也不例外,怎么越听越觉得IOC成了spring的专利了。。。
49 楼 robbin 2008-10-07  
axeon 写道
也许大家都不觉得这是个问题,为什么呢?有的人认为用接口是理所当然的,无需置疑的,有的人,比如我,就觉得这根本就是多余。

从观点上,这是学院派和实战派的区别,这是好听的话。

为什么出现这种现象,我想还是技术背景的问题。

第一个是时间界限:凡是02以后做java的,普遍都能接受类似struts,spring,hibernate之类的框架,02年之前做java的,接受并且使用这些框架是有些困难的。这是一个先入为主的问题,上来就用所谓ssh这些框架,哪里有时间和机会来思考和质疑呢?
第二个是语言界限:语言背景越是单一的,特别是只做过java的,越是对ssh深信不疑,以致崇拜。语言背景越是复杂的,比如做过c,delphi,php,.net,ruby的,越容易对ssh产生怀疑感。

任何一门技术,从最基础的经济学角度来说,都要满足多快好省的要求,才能不被淘汰,才能够淘汰别人。那么什么是多块好省呢?我的理解是要能够快速开发,运行还要高效。如果从这个观点来评判,我想思路会更加清晰的。

新技术的特性必然要有需求与此对应,否则这个新特性就是屠龙术,仅仅有可吹嘘的本钱。另外,这个需求首先应该是业务需求,而不是解决自身问题的。因为技术最终是为业务服务的,通过业务来体现技术价值。

首先肯定一点,JAVA本身并没有错,它仅仅是一门语言而已。

和同时期,早期一些,晚期一些的语言相比,java现在成绩如何呢?我想可以通过sourceforge上的开源项目数量来评判。如果从项目数量来看,我想php>perl>java吧?没准过几年ruby超越java也不是不可能。

有人说java的市场在企业级开发上,点点市面上的产品,又有多少家是抱着ssh开发的呢?

java这几年的失败,一方面是sun的问题,一方面也许就是定位所谓的企业级,还有一方面就是社团的注意力过多的关注在所谓的架构上,而不是产品应用上。

从多快好省的角度上来说,java当前所谓框架的代表ssh,引导的是一个开发慢,运行慢的技术派系,他的所谓维护性和扩展性(或许)优势是不明确的,甚至是不存在的。开发效率和运行效率是最大的软肋。

为什么会有“忽悠”,就是因为偷懒,不经大脑思考,就就跟风呼叫的人太多了,这误导了下一批人,因为众口铄金,皇帝的新衣面前,还有几人敢于说话?

技术浪潮总是几年来一次,大浪淘沙。有人站在最前面得利了,但是最傻的是后面跟着抬轿子的。所有的技术革新,你必须有先知先觉。

javaeye是怎么起来的?是因为ejb,一直到现在还有为ejb呼喊的jdon,当然,这个jdon还被好多人笑话过呢。我想当年ejb火的时候,你们肯定也像义和团一样保卫ejb。因为有的人压根就不用脑子思考,搞不清自己的站位,就连吵架,也是看哪边人多,就站在哪边的。

当然spring确实解决了一些问题,包括从版本发展的过程中也有所进化,甚至做了不少自我否定。跟着spring屁股后面否定自己,甚至有口难言的,我想都不在少数!

为什么要接口?除了隐藏实现,那么就是多态。如果使用spring,有什么好隐藏的?更因为编译器就绑定实现了,怎么玩多态?如果为了庞大而好看,我建议你一个类里只写一个方法好了!

为什么要继承?而不用调用?相比较继承,调用是更清晰的关系,除非是必要继承,没事儿你继承什么?

更不说大把人用的spring的beanFactory,更是笑死人了!这也是spring对他来说最重要的用处。首先如果只用单例,我干嘛不在类和方法上加上static?从实际使用上来说,spring通过hashmap来查找实例,而static是从内存直接调用,哪个更简单,效率更好,甚至零配置?

至于分层,更是笑话!曾经有一个帖子,抱怨招聘了一个技术高手,过来之后就会分层。结果招致群攻,简直笑死我了。我回了一个帖子,说了一句按需分层,竟然被评差贴。

一个项目的技术水平根本就不可以用是否使用ssh,是否分层来进行判断。更不说大把分层的代码里面仅仅是对上层的调用,但是如果程序需要改动,分层越多越难改,便于维护压根就是一个说辞。


从开始做java到现在,已经9年了。做的项目,有国家级的大项目,也有每日访问量500w的互联网项目,总结经验,ssh和项目质量,产品性能压根无关,也和项目维护更无关。倒是常见一些用ssh做互联网项目做的非常失败的,表现在开发速度慢,运行速度慢,系统运维难度大。

如果更公正的说,ssh可能适合一些小型的企业应用项目,除此,ssh和ssh倡导的一些理念丝毫排不上用场。




一、你拿Java和PHP/Perl比较是不公平的,一个是编译语言,一个是脚本语言。其实在企业应用软件市场,没有PHP/Perl的份。

二、你对SSH开源框架的蔑视也多少说明了一个拥有9年经验的古老的Java程序员对新技术(尽管SSH已经不新)与生俱来,发自内心的抵制,而且事实上你对Spring作为一个IoC容器的价值是没有领会到的。

三、尽管你口口声声抵制接口,但实际上你想抵制的真正目标并不是接口而是Spring,这体现在你一直声称应该用静态方法,而不是IoC容器上面。

四、不要过多摆资历,从某种意义上来说,摆资历是露怯的表现。

48 楼 robbin 2008-10-07  
axeon 写道
无状态的类为什么要实例化?
为什么不直接使用static调用?


很诧异你9年的Java经验,看来你对IoC也没有入门。 静态方法仅仅适合写工具类,而不适合写业务逻辑,对于应用程序来说,用静态方法是邪恶的,因为你无法注入依赖对象,迫使你自己在静态方法内部手工创建所有依赖对象,这是很糟糕编程实践。
47 楼 robbin 2008-10-07  
terranhao 写道
其实我也想了解下spring带来的真正的好处。
比如我IUserDAO dao=new UserDAO();
用spring 就是IUserDAO dao=beanFactory.getBean("userDAO");

假如以后我想把IUserDAO换成另外一种实现
IUserDAO dao=new UserDAO2();
对应spring: IUserDAO dao=beanFactory.getBean("userDAO2");

也许有人会说,我直接在spring的配置文件中将ID为userDAO的类的type改为UserDAO2就可以了,程序不用改动。但这又有什么太重大的优点呢?我用IDE的refactor一样可以马上将new UserDAO()换成new UserDAO2();

请问好处是什么?谁能告诉我?


其实像你这样用spring,等于spring根本没有入门。 Spring作为一个IoC的价值就在于消除工厂,结果你把Spring当成了一个大工厂来用。在Spring的思路来说,接口的意义在于:你不需要关心userDao是怎么来的,你可以直接拿到userDao。
46 楼 terranhao 2008-10-07  
完全不同意axeon的看法
计算机发展史就是分层史。

看看计算机网络七层协议(虽然有些死板,但是至少现在网络协议是建立在它之上的)

这里抛出一个定理:任何计算机问题都可以通过中间件解决。
这个定理难道不是说明了分层的niubility吗?
45 楼 sunarrow 2008-10-07  
我想说,并不是说使用了接口或者使用了SSH就是一个设计好的项目--

最近比较长的时间 都在弄JSP的老项目,发现如果设计得好,有封装得比较好用的工具类--JSP比SSH好使多了,开发速度快,跑起来也快
44 楼 axeon 2008-10-07  
terranhao 写道
terranhao 写道
其实我也想了解下spring带来的真正的好处。
比如我IUserDAO dao=new UserDAO();
用spring 就是IUserDAO dao=beanFactory.getBean("userDAO");

假如以后我想把IUserDAO换成另外一种实现
IUserDAO dao=new UserDAO2();
对应spring: IUserDAO dao=beanFactory.getBean("userDAO2");

也许有人会说,我直接在spring的配置文件中将ID为userDAO的类的type改为UserDAO2就可以了,程序不用改动。但这又有什么太重大的优点呢?我用IDE的refactor一样可以马上将new UserDAO()换成new UserDAO2();

请问好处是什么?谁能告诉我?

想了一会,发现自己犯傻了。
如果有UserDAO2有依赖的话,用spring只需要配置一下就可以了。
但是如果不用,那需要手工修改每一处设置依赖关系。(如果依赖很多,那么代码修改量就很大了)
看起来spring还是有很大的好处的。


无状态的类为什么要实例化?
为什么不直接使用static调用?
43 楼 terranhao 2008-10-07  
terranhao 写道
其实我也想了解下spring带来的真正的好处。
比如我IUserDAO dao=new UserDAO();
用spring 就是IUserDAO dao=beanFactory.getBean("userDAO");

假如以后我想把IUserDAO换成另外一种实现
IUserDAO dao=new UserDAO2();
对应spring: IUserDAO dao=beanFactory.getBean("userDAO2");

也许有人会说,我直接在spring的配置文件中将ID为userDAO的类的type改为UserDAO2就可以了,程序不用改动。但这又有什么太重大的优点呢?我用IDE的refactor一样可以马上将new UserDAO()换成new UserDAO2();

请问好处是什么?谁能告诉我?

想了一会,发现自己犯傻了。
如果有UserDAO2有依赖的话,用spring只需要配置一下就可以了。
但是如果不用,那需要手工修改每一处设置依赖关系。(如果依赖很多,那么代码修改量就很大了)
看起来spring还是有很大的好处的。
42 楼 axeon 2008-10-07  
也许大家都不觉得这是个问题,为什么呢?有的人认为用接口是理所当然的,无需置疑的,有的人,比如我,就觉得这根本就是多余。

从观点上,这是学院派和实战派的区别,这是好听的话。

为什么出现这种现象,我想还是技术背景的问题。

第一个是时间界限:凡是02以后做java的,普遍都能接受类似struts,spring,hibernate之类的框架,02年之前做java的,接受并且使用这些框架是有些困难的。这是一个先入为主的问题,上来就用所谓ssh这些框架,哪里有时间和机会来思考和质疑呢?
第二个是语言界限:语言背景越是单一的,特别是只做过java的,越是对ssh深信不疑,以致崇拜。语言背景越是复杂的,比如做过c,delphi,php,.net,ruby的,越容易对ssh产生怀疑感。

任何一门技术,从最基础的经济学角度来说,都要满足多快好省的要求,才能不被淘汰,才能够淘汰别人。那么什么是多块好省呢?我的理解是要能够快速开发,运行还要高效。如果从这个观点来评判,我想思路会更加清晰的。

新技术的特性必然要有需求与此对应,否则这个新特性就是屠龙术,仅仅有可吹嘘的本钱。另外,这个需求首先应该是业务需求,而不是解决自身问题的。因为技术最终是为业务服务的,通过业务来体现技术价值。

首先肯定一点,JAVA本身并没有错,它仅仅是一门语言而已。

和同时期,早期一些,晚期一些的语言相比,java现在成绩如何呢?我想可以通过sourceforge上的开源项目数量来评判。如果从项目数量来看,我想php>perl>java吧?没准过几年ruby超越java也不是不可能。

有人说java的市场在企业级开发上,点点市面上的产品,又有多少家是抱着ssh开发的呢?

java这几年的失败,一方面是sun的问题,一方面也许就是定位所谓的企业级,还有一方面就是社团的注意力过多的关注在所谓的架构上,而不是产品应用上。

从多快好省的角度上来说,java当前所谓框架的代表ssh,引导的是一个开发慢,运行慢的技术派系,他的所谓维护性和扩展性(或许)优势是不明确的,甚至是不存在的。开发效率和运行效率是最大的软肋。

为什么会有“忽悠”,就是因为偷懒,不经大脑思考,就就跟风呼叫的人太多了,这误导了下一批人,因为众口铄金,皇帝的新衣面前,还有几人敢于说话?

技术浪潮总是几年来一次,大浪淘沙。有人站在最前面得利了,但是最傻的是后面跟着抬轿子的。所有的技术革新,你必须有先知先觉。

javaeye是怎么起来的?是因为ejb,一直到现在还有为ejb呼喊的jdon,当然,这个jdon还被好多人笑话过呢。我想当年ejb火的时候,你们肯定也像义和团一样保卫ejb。因为有的人压根就不用脑子思考,搞不清自己的站位,就连吵架,也是看哪边人多,就站在哪边的。

当然spring确实解决了一些问题,包括从版本发展的过程中也有所进化,甚至做了不少自我否定。跟着spring屁股后面否定自己,甚至有口难言的,我想都不在少数!

为什么要接口?除了隐藏实现,那么就是多态。如果使用spring,有什么好隐藏的?更因为编译器就绑定实现了,怎么玩多态?如果为了庞大而好看,我建议你一个类里只写一个方法好了!

为什么要继承?而不用调用?相比较继承,调用是更清晰的关系,除非是必要继承,没事儿你继承什么?

更不说大把人用的spring的beanFactory,更是笑死人了!这也是spring对他来说最重要的用处。首先如果只用单例,我干嘛不在类和方法上加上static?从实际使用上来说,spring通过hashmap来查找实例,而static是从内存直接调用,哪个更简单,效率更好,甚至零配置?

至于分层,更是笑话!曾经有一个帖子,抱怨招聘了一个技术高手,过来之后就会分层。结果招致群攻,简直笑死我了。我回了一个帖子,说了一句按需分层,竟然被评差贴。

一个项目的技术水平根本就不可以用是否使用ssh,是否分层来进行判断。更不说大把分层的代码里面仅仅是对上层的调用,但是如果程序需要改动,分层越多越难改,便于维护压根就是一个说辞。


从开始做java到现在,已经9年了。做的项目,有国家级的大项目,也有每日访问量500w的互联网项目,总结经验,ssh和项目质量,产品性能压根无关,也和项目维护更无关。倒是常见一些用ssh做互联网项目做的非常失败的,表现在开发速度慢,运行速度慢,系统运维难度大。

如果更公正的说,ssh可能适合一些小型的企业应用项目,除此,ssh和ssh倡导的一些理念丝毫排不上用场。

相关推荐

    调用接口怎么知道使用的是哪个实现类.doc

    调用接口怎么知道使用的是哪个实现类 Java通过接口调用方法的时候,怎么知道调用的是哪个实现类 当调用接口中的方法时,如何判定用的是哪个实现类 一个接口有多个实现类,怎么知道调用了哪个实现类

    面向接口编程而不是面向实现编程

    4. **使用接口**:在需要的地方,我们使用实现了接口的对象,而不是直接创建实现类的实例。这样,我们的代码对具体实现保持无知,增强了灵活性。 5. **配置和管理**:在应用的配置中,我们可以指定哪些实现类应该被...

    Java多态和实现接口的类的对象赋值给接口引用的方法(推荐)

    - 当通过接口引用调用方法时,该方法必须在接口中已经声明,并且在实现类中的实现必须与接口中定义的完全一致。 - 子类可以重写父类的方法,但这并不意味着父类引用不能调用子类的其他方法。如果子类有特有的方法,...

    实现接口的匿名类

    4. **匿名类实现接口**:在创建对象时直接实现接口,不需要声明单独的类,常用于内部类和回调函数。 5. **方法调用**:通过接口引用调用方法,实际执行的是实现该接口的具体类的对象的方法。 理解这些概念对于深入...

    net 接口实现,接口定义,接口和类,接口,类

    接口的使用使得代码更加灵活,易于扩展,同时也支持多继承,这是类无法直接实现的。本文将深入探讨.NET中的接口实现、接口定义、接口与类的关系,以及接口与类的区别。 ### 接口定义 接口通过`interface`关键字...

    5. 多个service实现同一个接口 或者抽象类 1

    这两个实现类都使用了Spring的`@Service`注解,标记为Spring管理的bean。`@Service`注解通常用于表示业务层的服务类。在这里,它们分别注入了不同类型的`OAXmlDealHandle`实现,通过`@Resource`注解来指定类型,分别...

    Java 接口和抽象类

    然后,我们创建了两个具体实现类:Human 和 Monkey,它们都继承了 LivingThing 抽象类。在 Human 和 Monkey 中,我们实现了抽象方法 dance(String dancingStyle)。 接口 接口是一种特殊的抽象类,它不能被实例化,...

    DLL导出类的三种方法,导出接口类,导出类指针,导出类,不建议使用导出类

    本篇将详细讲解DLL导出类的三种常见方法:导出接口类、导出类指针以及导出类,并说明为什么通常不建议直接导出类。 1. 导出接口类 接口类(Interface Class)是一种只包含纯虚函数的抽象基类,不包含任何数据成员...

    匿名内部类实现接口回调

    匿名内部类是Java中的一种特殊类,它没有名称,可以直接实例化,并且可以继承一个类或实现一个(多个)接口。在接口回调的场景下,我们可以使用匿名内部类快速地创建一个实现了接口的实例,而无需定义一个新的类。...

    UML类图中的接口与接口实现

    如果属性不是公共的,则实现接口的分类器不需要显式定义这些属性,只需要保证其实现符合接口的要求即可。 2. **定义关联**:当接口定义了一个关联时,所有实现该接口的分类器都必须实现这个关联。这意味着,实现...

    ArcGIS Engine 9.1类,接口一览表

    一个实现类一般实现了相当多的接口,为了避免所实现的接口出现方法重名,另外对这些方法有好的分类,故把实现类对象赋值给接口类型的对象,而不是直接用类来创建对象。由于创建的对象是某个接口类型的,则这个对象就...

    子接口及其实现类PPT实用.pptx

    本节将深入探讨`Collection`接口及其常用的子接口与实现类。 首先,`Collection`接口概述:它是Java集合框架的根接口,定义了集合的基本操作,如添加、删除和遍历元素。所有集合类都直接或间接地继承自`Collection`...

    动态实现接口

    接口通过`interface`关键字定义,而类通过`implements`关键字实现接口。 2. **反射(Reflection)** 反射是.NET框架提供的一种能力,允许程序在运行时获取类型信息,并能创建和操作这些类型实例。`System.Type`类...

    java 实现接口和继承关系

    如果实现类是抽象类,则可以选择部分实现或者不实现接口中的方法。 #### 示例 假设有一个接口`Animal`,其中包含一个抽象方法`makeSound()`。 ```java public interface Animal { void makeSound(); } ``` 可以...

    idea实现类快捷生成接口方法示例

    除了上述直接生成方法的方式,Idea 还提供了其他一些与接口相关的快捷操作,例如在实现类中快速导航到接口方法(`Ctrl + B`),或者查看接口的实现类列表(`Ctrl + H`,选择 "Implementing Classes")等。...

    C++接口实现总结

    这样做的好处是保持接口的纯粹性,确保所有实现该接口的类只关注接口定义的行为,而不会受到额外数据成员的影响。 6. **智能指针与接口**:在C++11及更高版本中,使用智能指针(如`std::unique_ptr`和`std::shared_...

    c# 中抽象类和接口的学习

    1. **实例化**:抽象类不能直接实例化,而接口也不能实例化,但是任何类都可以实现接口,而无需继承。 2. **成员实现**:抽象类可以包含抽象和非抽象成员,而接口只能包含抽象成员。 3. **继承限制**:C#中一个类...

    完美C语言接口源码实例实现接口实例

    实现接口的类或函数需要遵循接口定义的函数指针类型,提供相应的函数实现。在使用时,通过接口结构体的实例,调用其内部的函数指针,达到调用实际函数的目的。 6. **多态性**: 尽管C语言没有内置的多态机制,但...

    Java基础--接口类

    静态方法不属于接口的任何实现类,而是直接通过接口调用。 ```java public interface MyInterface { static void staticMethod() { System.out.println("执行静态方法"); } } ``` 6. 接口与多态: 接口是多态性...

    Java 接口 内部类

    接口可以继承多个其他接口,实现多继承的功能,但不能继承类或实现其他非接口的实体。 内部类,也称为嵌套类,可以在类的内部定义,分为静态内部类和非静态内部类(也叫成员内部类)。非静态内部类可以直接访问外部...

Global site tag (gtag.js) - Google Analytics