Eric Raymond对于几大开发语言的评价

标题   Eric Raymond对于几大开发语言的评价     选择自 myan 的 Blog
关键字   C, C++, Java, Python
出处   http://www.catb.org/~esr/writings/taoup/html/ch14s04.html#c_language

【译者注】


Eric Raymond是开源运动的领袖人物,对于UNIX开发有很深的造诣,主持开发了fetchmail。他的《大教堂与集市》被奉为开源运动的经典之作。下 面对几大开发语言的评价非常中肯,是我近年来看到的比较出色的评论。特别是他评价中抱有的那种“简单就是好”的思想,很值得我们深思。我特别选译出一些段 落,供大家阅读思考。原文参见:http: //www.catb.org/~esr/writings/taoup/html/ch14s04.html#c_language

Raymond此文不是在泛泛地去谈语言的优劣,而是要回答一个问题:在UNIX下开发开源项目,如何选择开发工具?我翻译的很零散,建议大家去看原文。

C
虽说C语言在内存管理方面存在严重的缺陷,不过它还是在某些应用领域里称王称霸。对于那些要求最高的效率,良好的实时性,或者与操作系统内核紧密关联的程序来说,C仍然是很好的选择。

C良好的可移植性也为它加了分。不过现在很多其他的语言可移植性越来越好,C在这方面的优势可能会逐渐丧失。

现有的很多程序可以产生非常棒的C代码,比如语法分析器、GUI Builder等,这时候C语言也是有吸引力的,因为你所需要编写的代码只是整个程序的一小部分。

再有,我们当然应该认识道,C语言对于程序员来说具有无可替代的价值。就我这里讨论的每一种语言而论,只要你发掘的足够深,到最后你会看到它们的内核都是用纯正的、可移植的C写成的。

到了今天这个时候,我们最好把C看成是UNIX虚拟机上的高级汇编语言。

就算是其他的高级语言完全可以满足你的工作需要,抽出时间来学习C语言也仍然有益,它能帮助你在硬件体系的层次上思考问题。

即使到了今天,最好的C语言教程仍然是1988年出版的K&R第二版The C Programming Language.

总结:C最出色的地方在于其高效和贴近机器,最糟糕的地方在它的内存管理地狱。

C++
C++最初发布于1980年代中期,当时面向对象语言被认为是解决软件复杂性问题的银弹。C++的面向对象特性看相去使其全面超越了C,支持者认为C++将迅速把上一代语言挤到陈列馆里去。

但是历史并非如此。究其原因,至少有一部分归咎于C++本身。为了与C兼容,C++被迫作出了很多重大的设计妥协,结果导致语言过分华丽,过分复杂。为了与C兼容,C++并没有采用自动内存管理的策略,从而丧失了修正C最严重问题的机会。

另外一部分原因,恐怕要算到面向对象身上。看起来OO并没有很好的达成人们当年的预期。我就这个问题调研过,我发 现使用OO方法导致组件之间出现很厚的粘合层,并且带来了严重的可维护性问题。今天让我们来看看开放源码社区,你会发现C++的应用还是集中在GUI,游 戏和多媒体工具包这些方面,在其他地方很少用到。要知道,面向对象也只是在这些领域被证明非常成功,而开放源码社区的选择,很大程度上体现了程序员的自由 意志,而不是公司管理层的胡乱指挥。

也许C++实现OO的方法有问题。有证据表明C++程序在整个生命周期的开销高于相应的C, Fortran和Ada程序。不过,究竟这是否应该归咎与C++的OO实现上,还不清楚。

最近几年,C++加入了很多非OO的思想,其异常思想类似Lisp,STL的出现是非常了不起的。

其实C++最根本的问题在于,它基本上只不过是另一种传统的语言。STL中的内存管理比先前的new/delete和C的方案要好的多,但是还是没有解决问题。对于很多应用程序而言,其OO特性并不明显,相比与C,除了增加复杂度之外没有获得很多好处。

总结:C++优点在于作为编译型语言,把效率与泛型和面向对象特性结合起来,其缺点在于过于华丽复杂,倾向于鼓励程过分复杂的设计。

Java
Java的设计很聪明,它采用了自动内存管理,这是最大的改进,支持OO设计带来的好处虽然不那么突出,不过也很值得赞赏,相比C++,其OO设计规模小而且简单 。

相对于Python而言,Java有一些明显的失误。有些地方设计的还是太复杂,甚至有缺陷。Java的类可见性和隐式scoping规则太复杂 了。Interface机制是为了避免多继承带来的问题而设计的,但是要理解和使用它还是挺难。内部类和匿名类导致令人困惑的代码。缺乏有效的析构机制, 使得除了内存之外的其他资源(比如互斥量和锁)管理起来很困难。Java的线程不可靠,其I/O机制很强大,但是读取一个文本文件却非常繁琐。

Java没有管理库版本的机制,从而形式上重蹈了了Windows DLL地狱的覆辙。在类似应用服务器这样的环境里,这引起了大量的问题。

总体而言,我们可以说除了系统编程和对效率要求极高的程序之外,Java在大部分领域优于C++。经验表明,Java程序员似乎不太容易象C++程序员那样构造过度的OO层,不过在Java中这仍然是个严重问题。

Java是否优于诸如Perl, Python这样的语言?我们还不是很清楚,很大程度上似乎跟程序规模有关。其擅长的领域基本上于Python相似,在效率上无法跟C/C++相提并论, 在小规模的、大量使用模式匹配和编辑的项目里也无法匹敌Perl。在小项目里,Java显得过分强大了。我们猜测Python更适合小项目,而Java适 合大项目,不过这一点并没有得到有力的证明。

Python
Python是一种脚本语言,可以与C紧密整合。它可以与动态加载的C库模块交换数据,也可以作为内嵌脚本语言而从C中调用。其语法类似C和模块化语言的杂合,不过有一个独一无二的特征,就是以缩进来确定语句块。

Python语言非常干净,设计优雅,具有出色的模块化特性。它提供了面向对象能力,但不强迫用户进行面向对象设计。其类型系统提供了强大的表达能 力,类似Perl,具有匿名lambda表达式,这点又让Lisp黑客们感到亲切。Python依靠Tk提供方便的GUI界面开发能力。

在所有的解释型语言里,Python和Java最适合多名程序员以渐进方式协同开发大型项目。在很多方面,Python比Java要简单,它非常适合与构造快速原型,这一点使得它对于Java有独特优势:对于那些既不很复杂,又不要求高效率的程序,Python十分合适。

Python的速度没法跟C/C++相比,不过在今天的高速CPU上,合理地使用混合语言编程策略使得Python的上述弱点被有效地弥补。事实 上,Python几乎被认为是主流脚本语言中最慢的一个,因为它提供了动态多态性。在大量使用正则表达式的小型项目,它逊于Perl。对于微型项目而言, shell和Tcl可能更好,Python显得太过强大了。

总结:Python最出色的地方在于,它鼓励清晰易读的代码,特别适合以渐进开发的方式构造大项目。其缺陷在于效率不高,太慢,不但跟编译语言相比慢,就是跟其他脚本语言相比也显得慢。

 

对该文的评论:

By vrman
阐 述我的一些意见之前,先摆明一下立场,我热爱C++语言,而且长时间使用它。从较低层次的角度讲,对STL/ATL/WTL/MFC都有长时间的使用,对 ACE/Boost/Loki的结构也都有一点点浅显的探索。由于热爱C++,因此我对java和c#这两种从语法上非常相似于C++的语言同样保有好 感,并在适当的场合也会用他们开发一些大大小小的程序,但对他们的高级语言特性涉猎不算太深(我觉得从语言学角度讲他们都比C++简单好学)。

  其实单纯的对比语言意义不是很大,关键是结合特定应用场合的去对比。我初步分为三块:A.语法及语言对设计的影响及自身特性。B.相关类库的水平。 C.IDE等综合开发运行环境的特性。Eric其实对C++也不能算有太多的偏见,他只是针对一些目前的应用现状判断C++的劣势和优势对比其它语言来说 不是太有利而已。比如对MIS/OA之类的数据库程序似乎用一些相对C++语法更简单自闭的、注重程序开发效率(开发成本)和健壮性(维护成本)的语言更 有优势而已。

对于语言自身特性上
------------------
  我个人比较关注:A.面向对象的表达能力。B.语法的严谨性。C.语言易学易用性。D.开发健壮程序的难度。E.设计合理架构的难度。F.灵活性和内涵。
  A.C++的表达能力最强,但他的表达能力强也带来了很多隐患。这一点要看你写程序是为了什么啦。如果你写程序是为了展示自己的OO才华,C++确实 是目前出现过的表达能力最强大的OO语言之一。不过如果是一个OO的入门者,用C++设计出看上去非常不合理的表达也就很容易。但本条只反应语言自身的能 力,我认为C++明显优于其它多数OO语言。
  B.严谨性。C++不是特别优秀,他的语法中存在很多隐含、缺省、默认和假设(这些条件需要很高的学习代价才能掌握)。相比较java和c#要稍微好一点点(他们的隐含、缺省、默认和假设是很少的,这让程序看上去更规整)。但是他们这方面都不能说特别好。
  C.语言易学易用性。仅说语法上,C++是很复杂的,甚至要大一个数量级(只要看书的厚度就知道了,^_^)。java/c#这方面要改良很多,去掉 了很多复杂的概念。我想java程序员没有必要去探究指向指针的指针,探究mutex、criticalsection之类的东东的。
  D.开发健壮程序的难度。从这个角度讲,对于一个熟练的有高超技巧的C++程序员,在一定的积累之后,他完全可能已经具备了使用方法跟java- object-reference相似的smartptr等等等等。(如loki库还有boost库里的类似东东)。如果所有的对象指针都替换为 smartptr,你还需要为垃圾收集么?虽然我承认培训一个有这种水平的程序员要难得多,但是这一条已经在C里面被统计了,我们不能在这里再统计一遍。 所以,我认为对两方面都是专家的程序员来说,两个语言在开发健壮程序的难度上差异将缩小很多,接近相等。
  E.设计合理架构的难度。分析原因跟D类似,不过这里面我要特别说明,实际上由于java/c#本身牺牲了类似于C++模板那样的强泛型机制和坚持了 单根继承机制,所以有时候难免会增加一些面向实现的抽象层次和代码实现的繁琐。对于高手来说,两个语言这方面的差异也很小,都不成问题。
  F.灵活性和内涵。毫无疑问C++这方面更强。他的生命力一直都很强,而且直到今天仍然在进化。这源于C++语法的灵活性。所以泛型、产生式编程、面 向接口和组件化等设计理论和方法都是在此C++强大表达的基础上产生的。所以,如果你想作一些创新和掌握更多的东西,那么C++是非常优秀的语言。

  综合来看,C++和java/c#各有千秋。我个人说一个可能有争议的观点,仅从语法角度讲,C++可能学成要难,但一旦学成之后的设计开发水平也将 是相对更强的。因为语言的表达能力强、限制小。java/c#则上手快,而且上手后稍有一些技能就很容易写出超越目前80-90%的C++程序员作品水平 的设计和实现。(这里的对比指不涉及数据库、网络等特定环境的程序,例如算法库、底层类库等)。

相关类库的水平
--------------
  先看标准库。C++的运行库水平很难评价,因为C++的标准化比较慢也比较晚。从目前来看还是相当慢的。而且库功能非常原始。我们承认STL的强大, 但是无疑我们发现STL虽然精巧,但是从规模上还有很多事情没有作。真正开发一个实用的数据库程序、网络程序、多线程程序、甚至协议解析器(字符串功 能),我们都无法满足于STL。
   java的标准库掌握在sun手中,所以发展快一些,但也存在一些缺陷。开发者不能完全信赖jdk的兼容性,甚至可以肯定的说jdk是不兼容的。比如你 如果自己作了一个数据库驱动,能够驱动jdk 1.3不代表它能驱动jdk 1.4,甚至更小的版本号也一样。
  如果看看微软对C++库的贡献,我们可以看看MFC/ATL/WTL。MFC的设计是划时代的,但从现代的程序设计观点,陈旧的败笔太多,而且完全依 赖于Windows。ATL-WTL改进了很多,但又太强化了COM的作用。而且现在泛型模板技术发展很快,Loki和boost也带来了很多新概念。所 以,个人感觉这方面的库不算太好。Borland的OWL似乎设计上要好一些。但是商业原因,这个库也没能大范围流传开来。
  所以,从标准库的水平上看C++要比C#和java弱。不过大家要理解,毕竟C++标准化很晚,而且MFC等成型的时间何其早。不过如果有人结合泛 型、设计模式发展了一个更强大和综合的库(boost、ace都有这种倾向),我觉得c++的标准库的水平是有可能提高到一个新的高度的。
  如果是第三方库,我觉得C++和java都很强,一般说来各类特定功能的库在两个语言中都存在对应的版本。我觉得倒是差别不大。如果考察特定应用,C ++在数据库的访问方面的表现我觉得要稍微比java稍微好一点(J2SE 1.4.2)。纯网络开发(不考虑性能),不太好判断,不过java库相对简 单好用,c++库相对功能完备,各有千秋吧。界面方面,仅论制作效果C++还是更强(无论windows下还是linux下),如果论界面系统的设计水平 和可维护性我觉得java还是很不错的(不说新技术,就SWING比MFC那种库强很多)。一般说来,java的库的bug相对较少。

IDE等综合开发运行环境
---------------------
  jbuilder和VC是比较商业化的两个大型平台,对比他们的功能特点是各有千秋,我觉得总体上jbuilder在UML、单元测试、文档化等方面 要比VC.NET 2003整体上强。调试方面两者差不多。但是纯粹说代码编辑、替换、查找之类的基础操作,VC似乎要稍微好用一点。VC自身的MSDN 的文档也比较强。比JDK的文档要详尽一些。此外,C++也可以跨平台,但是这种跨平台依赖于特定平台编译器的标准化程度和开发者对标准C++的熟悉程 度。java程序无论怎样将几乎注定可以跨平台(有JRE实现的情况下)。从目前来看,java被一些UML/MO之类的工具支持得相当好,可以正向逆向 功能,保持设计、实现同步等,而C++就要差很多。综合评价,我认为java这方面要稍微占优。当然,C++其实也有cppunit、doxygen、 together之类的辅助工具,但毕竟没有集成在IDE中,让很多新手不知所综。

  此外,要补充的是c++可以操作硬件和底层,在某些特定领域如性能敏感或设备敏感的领域,c/c++的优势目前仍然非常明显。

综述
----
1.一个C++的专家级高手可以轻松的(开发成本低)写出和java相似水平(设计好、稳定,维护成本低)的东西,甚至比java作的更好。反之,一个 java高手很难写出明显一个超越C++专家的作品(包括性能、可维护性、设计等等等等),但对大多数应用来说,两者可以作得一样好。
2.java入门比C++要容易,而且java初级程序员比较少犯像c++初级程序员犯得很多错误(语法理解和运用方面,比如滥用virtual、 const、引用、内存泄漏等等等等)。从商业公司的角度讲,培养一个商业java程序员要比培养可以作出同等水平的C++程序员便宜得多。
3.C++在通用类库设计水平方面受历史原因相对水平比较低,不过正在改善中,特别是STL、boost之类的库让我看到了一种希望和可能。

建议
----
  一个用C++很多年,仍然不能写出优雅程序的人说明你的天赋不适合使用C++这种语言,建议你使用java/c#之类的语言。
  对于一个新学习编程和面向对象设计的人,我不作推荐。因为用java和用C++都可以,也取决于你的学习方法和天赋。
  一个用C++已经很熟练很少犯低级错误,但是仍然在不断被各种新思想左右的人,建议你深入研究设计模式、泛型开发、产生式编程和C++的语言机制,然 后再决定是否放弃C++。如果不放弃的话,建议你要用比较高的水平去积累自己的类库或者研读使用boost、ace之类的先进类库,不要把太多心思花在 MFC上。
  对于一个作性能不敏感侧重业务逻辑、侧重设计的公司,建议用java之类的语言作内核。无论是开发设计及管理的整套工具,还是人员的培训成本都要低很多。
  对于只关注作一些高性能程序的人或者跟硬件打交道的人,比如指令集优化级别的、驱动程序、3D程序,建议你坚持C++。
  对于在windows下编程为主的人,特别是界面类开发占很大比例的人(比如作一个photoshop、cad),鼓励你使用
C#.NET(个人不太喜欢VB.NET,其实是差不多的)。

posted @ 2005-09-14 11:01  shipfi  阅读(962)  评论(0)    收藏  举报