不是又一篇 C# 与 VB 的文章






3.88/5 (251投票s)
2005年4月16日
21分钟阅读

1098473
这无关乎功能支持,而关乎文化。
目录
引言
本文解释了 Microsoft .NET 应用程序开发组织采用 C# 编码相对于采用 VB 编码的优势。
众所周知,VB.NET 和 C# 在功能上是等效的。因此,一个经常听到的选择其一的论点是,既然它们功能等效,那么两者都没有明显的优势。这个论点有其道理,但因为它试图保持中立,避免主观看法,所以未能触及问题的核心。
本文不仅仅考虑客观论点。相反,我试图探讨一些影响 VB 和 C# 开发人员的高度主观的因素。这些主观因素随着时间的推移共同作用,形成了一种特定的文化。VB 的文化与 C# 的文化是不同的。
通过审视这两种文化历史及其当前趋势,我们可以预测选择一种语言或另一种语言可能会如何影响生产环境中高质量代码的产出。
Visual Basic 的文化
Visual Basic 的目的是为软件开发工具创造一个大众市场。在 Visual Basic 出现之前,应用程序开发语言被认为是复杂的,仅限于熟练程序员的领域。Visual Basic 语法简单,使得几乎任何人都可以在几个小时内学会如何创建简单的应用程序。在那个软件开发更多地被看作一门玄学而非工程学科的时代,能够加入“软件开发者”行列的能力对许多计算机用户来说是一种强大的诱惑。
而他们确实加入了。数以百万计的计算机“高级用户”变成了数以百万计的“软件开发者”。恰逢其时,Visual Basic 的出现正值对新软件应用的需求急剧增长,推动了需求,从而提高了软件开发人员的薪水。
Visual Basic 缺乏面向对象编程的基本构建块,这一点在当时并不重要。软件还相对简单。分布式应用程序开发充其量是客户端-服务器模式。网络是如此新颖,以至于它的应用程序开发模型几乎还未开始演变——商界甚至不知道网络将走向何方,那么开发人员又怎么可能知道如何为之编程呢?Web 应用程序是凑合出来的,但这没关系。使这种凑合的方法论雪上加霜的是,对 Web 应用程序的需求开始以超出最疯狂预期的数量级加速增长。应用程序开发人员的薪水飞涨,需求持续增加,而对一个理智、可持续的应用程序开发模型的需求被远远抛在了后面。
这一趋势的顶峰与互联网泡沫的顶峰相吻合。大批技能严重不足的开发者被支付巨额薪水,并被提升到近乎狂热的地位,去拼凑任何勉强看起来像软件应用的东西。而 Visual Basic,由于其缺乏规范和约束,不会减慢这种拼凑过程,恰好迎合了这股狂热。
Visual Basic 于1991年3月推出。2000年,微软宣布了 .NET,这一举动彻底推翻了旧有格局,用一个实际上全新的开发范式取代了 Visual Basic。程序员所依赖的底层类库被 .NET 框架完全取代。那些笨拙的第三方工具被扫地出门,取而代之的是一个清晰的第三方工具模型。由于 Visual Basic 引擎架构的底层限制而多年来强制执行的继承缺失和多态有限实现,通过彻底抛弃旧引擎而得以克服。
随着这些变化,Visual Basic 重生为一个强大的新开发平台,功能上等同于 C#、J# 和 Java。事实上,在90年代的 Visual Basic 中,今天只剩下两样东西:文化和语法。Visual Basic 的文化是90年代的文化:快速构建,大肆宣传,卖掉它,不要担心这个故事明天是否还能站得住脚,甚至根本站不住脚。
要理解这种文化如何影响软件开发的趋势,听听尼克劳斯·维尔特 (Niklaus Wirth) 在1997年对此的看法是很有启发性的。尼克劳斯·维尔特是软件界最具影响力的思想家之一。作为苏黎世联邦理工学院的教授,维尔特设计了 Pascal、Modula 2 和 Oberon。在20世纪70年代初,他是提倡通过逐步求精进行程序开发的人之一。他是许多重要著作的作者,包括《算法+数据结构=程序》(Prentice Hall, 1975) 和《系统化编程》(Prentice Hall, 1973)。他于1984年获得图灵奖,并获得了五个荣誉博士学位及其他多项奖项。
在1997年6月发表于《软件开发》杂志的一篇著名访谈中,卡洛·佩西奥 (Carlo Pescio) 博士问维尔特:
您可能知道由 Yourdon 推广的“足够好的软件”概念。在许多方面,这只是对软件世界现状的一种合理化解释:第一个将功能丰富的产品推向市场的公司比谨慎、追求质量的公司更有可能赢得竞争。您认为开发人员和软件组织对此能做些什么吗?我想许多开发人员会乐意有更多的时间来开发更好的软件,但同时他们又因公司生存的名义而被迫赶工。“教育用户”似乎更像一个不切实际的梦想,而非一种可能性。
维尔特回答道:
“足够好的软件”很少是真正足够好的。这是现代精神的一种可悲体现,在这种精神中,个人对其工作的自豪感已变得罕见。一个人可能从其成功的工作中获得满足感,因为那项工作是巧妙的、优美的,或仅仅是令人愉悦的,这种想法已经变得可笑。除了经济上的成功和金钱回报,没有什么是可以接受的。因此,我们的职业已变成了纯粹的工作。但工作质量只能通过个人满足感、奉献精神和乐趣来期待。在我们的行业中,精确和完美不是可有可无的奢侈品,而是一种简单的必需品。
最近,我读了一份由瑞士国家科学基金会资助的研究项目的最终报告。该项目的幼稚目标被确定如下:首先,如何实现简易编程(特别是对非专家而言)?其次,如何实现一种机制,可以隐藏并行编程的难点?经过30多年的编程,我们应该知道,复杂软件的设计本质上是困难的。尽管几十年来,业界一直在宣传程序员职位时声称编程是容易的。后来,当连广告商都产生怀疑时,他们转而承诺提供各种各样的工具来简化这些艰巨的任务。工具成了口号;正确的工具,配上聪明的技巧和严肃的管理方法,就能创造奇迹。然后,艾兹格·迪科斯彻 (Edsger Dijkstra) 称软件工程为‘尽管你不会编程,但还是要编程’。
事实上,软件工程的困境并非由于缺乏工具或适当的管理,而主要是由于缺乏足够的技术能力。一个好的设计师必须依赖经验、精确的逻辑思维和一丝不苟的严谨。任何魔法都无济于事。鉴于此,尤其可悲的是,在许多信息学课程中,大型编程被严重忽视。设计已成为一个无人问津的话题。结果,软件工程成了黑客的天堂。一个程序看起来越混乱,有人费心去检查和揭穿它的危险就越小。”
稍后,我们将探讨 Visual Basic 的文化如何影响至今所产生的代码质量,以及 Visual Basic 仅存的遗迹——语法——如何不幸地继续强化这种文化。
但首先,让我们回顾一下 C# 的文化。
C# 的文化
要理解 C# 的文化,就要理解其首席架构师安德斯·海尔斯伯格 (Anders Hejlsberg) 的故事。海尔斯伯格深为敬佩尼克劳斯·维尔特。维尔特从 Algol 创造了 Pascal 语言,这是第一门具有可读、结构化和系统定义语法的高级语言。海尔斯伯格为 Pascal 创造了世界上第一个编译器,并将该语言扩展到包含面向对象的能力(Object Pascal)。他们都专注于语言的优雅性,部分原因是因为该语言被设计为一种教学工具,供编程语言专业的学生学习结构化,以及后来的面向对象开发技术。
Pascal 最初被嵌入到 Borland 的商业开发环境中,随着1983年11月 Turbo Pascal 的发布,该产品通过授权协议使用了海尔斯伯格的编译器。从1983年到1996年,海尔斯伯格在 Borland 工作了十三年,期间他是 Turbo Pascal 以及后来的 Delphi 的首席架构师。
Delphi 是 Visual Basic 的直接竞争对手,在技术上被认为远胜一筹,甚至微软也这么认为,他们经常剽窃 Delphi 的发明。人们普遍认为,要想预知每个新版 Visual Basic 的一些特性,只需看看当前版本的 Delphi 就行了。
然而,Delphi 受限于相对微不足道的开发和广告预算。当微软投入数亿美元推广 Visual Basic 时,Borland 不得不主要依靠技术卓越性通过口碑来推动使用。海尔斯伯格知道,只要他还在 Borland,他的作品就永远无法获得主流的认可。与此同时,微软逐渐意识到,没有海尔斯伯格,Visual Basic 永远无法达到 Delphi 的技术卓越水平。
大约在这两种力量开始将海尔斯伯格和微软拉到一起的时候,一声惊雷击下,极大地加速了他们的融合。这声惊雷就是马克·安德森 (Marc Andreessen) 对一门全新语言(或至少是一个有着全新名字的语言)的认可:Java。
Java 的前身是由 Sun 公司的帕特里克·诺顿 (Patrick Naughton)、迈克·谢里丹 (Mike Sheridan) 和詹姆斯·高斯林 (James Gosling) 在1990-92年间开发的。他们当时有一个极具远见的想法,即用一种通用的编程语言将小型设备,如录像机和电视机,在网络空间中连接起来。Java 的第一个版本叫做“Oak”,它架构中立、分布式、可移植、面向对象且安全。尽管这些特性后来被证明正是开发 Web 应用程序所需要的,但 Oak 在 Web 上的应用要等到1994年。但 Oak 的真正潜力需要数年才能被认识到,这一点远没有它诞生的文化重要。因为在1990年,诺顿对 Sun 公司的发展方向分歧感到恼火,几乎要辞职并将他的工作带到史蒂夫·乔布斯拥有的、更理想化、更专注的 NeXT 公司。正是因为 Sun 的 CEO 斯科特·麦克尼利 (Scott McNealy) 向诺顿征求了一份关于 Sun 失败之处的报告,并听取了报告的建议,诺顿才留了下来。麦克尼利同意诺顿可以在 Sun 主流之外组建一个小型工程师团队,以便“少做点事,但做得更好”。
由一个致力于技术卓越的小团队设计的 Oak/Java,是 Visual Basic 的对立面。是的,它更难学,但它更强大。事实胜于雄辩。由熟练的 Java 开发人员架构和构建的 Java 应用程序,比绝大多数 Visual Basic 应用程序更强大、功能更丰富。
网景公司 (Netscape) 的 CEO,也就是当时“互联网之神”的马克·安德森,是看到这门新语言潜力的人之一。1994年,他告诉《圣何塞信使报》:“这些家伙正在做的事情是无可否认、绝对全新的。这是伟大的东西。”
如果来自大多数人,这样的认可不过是又一个火花。但来自安德森,这就是一道惊雷,震惊了世界,引发了对 Java 近乎狂热的采纳,并最终促使微软和海尔斯伯格走到了一起。
因为 Java 也并非完美,而那时才华横溢的海尔斯伯格正在构想下一代应用程序开发语言。海尔斯伯格设想了一种语言,它将通过使组件开发的三个关键构造——属性、方法和事件——成为语言的一等公民,从而完全拥抱新兴的组件模型。
例如,在 Java 中,属性并不真正存在。它们是通过使用 get xxx
和 set xxx
语法来“伪造”的。在属性检查器中,它们显示为“xxx”,你必须知道要将 get
和 set
放在正确的位置。这一点以及其他不规范之处让追求完美的海尔斯伯格感到不适。他认为理想的语言不应需要这样的权宜之计或变通方法,而应将所有核心构造直接融入语法中,给程序员一种“一站式”的体验。问题在于,这将需要对编译器进行根本性的重构,以及巨大的研发开销。
随着 Java 迅速占领市场,到1996年,微软开始感到非常担忧。他们对一门优雅、精确、需要相当程度的编程技巧和奉献精神才能有效使用的语言能够与 Visual Basic 抗衡感到措手不及。他们也认识到,他们需要的不仅仅是对 Visual Basic 引擎的一些改造,而是根本性的变革。他们向海尔斯伯格提出了一个他无法拒绝的条件。如果他来微软,他将获得一张白纸和一个庞大的预算,来创造一个“完美”版本的 Java。1996年,海尔斯伯格开始作为首席架构师,着手开发微软的 J++ 6.0 和 WFC(Windows Foundation Classes for Java)。
微软 J++ 6.0 和 WFC,源于世界上最有资格的软件架构师渴望将非常好的 Java 变得更好的强烈愿望,是 Object Pascal 和 Delphi 可视化组件库的继承者。并且很快,它们将成为 C# 和 .NET 框架的先驱。
因为在1997年,Sun 公司起诉微软对其 Java 所做的修改,导致这项工作戛然而止。
微软并未因此却步,凭借其雄厚的财政储备,并想与 Sun 公司一较高下,他们加大了赌注。它给了海尔斯伯格一张更干净的白纸,授权他编写一种比 Java 更好的新语言,并由一个比 Java 更好的编程工具包支持。
其结果,诞生于一种将技术卓越放在首位的文化中,不受先前约束的束缚,并由海尔斯伯格多年来在 Turbo Pascal 和 Delphi 上的经验智慧以及从 Java 中汲取的智慧所指导,便是 C# 语言。
语法、语义和文化惯性
我们已经看到 VB 和 C# 的文化非常不同。而且我们也看到,这并不是使用它们的程序员的错。相反,这是多种因素共同作用的产物,这些因素可以统称为它们的成长环境——商业环境、目标市场、原始语言开发者的正直和背景,以及无数其他因素。
然而,有一个因素似乎比其他因素对文化的影响更大,那就是语言的语法和语义。
语法和语义在多大程度上影响了围绕一门语言建立起来的文化,反之,语法和语义在多大程度上又依赖于该语言被创造时的文化?
事实是,两者兼而有之——就像口语既源于文化又影响文化一样。例如,在遥远的北方,语言语法已经演化出几个词来表示不同类型的雪。然后,人们在互动中使用这些词语来表达雪的细微差别,从而创造了一种更以雪为中心的文化。
因此,在 Visual Basic 中,决定在语法和语义中包含直接将数字赋给字符串(反之亦然)的能力,是设计者希望吸引那些可能不理解强类型变量概念的广大开发者的结果。一旦语法允许了这样做,这种赋值就变得普遍,从而强化了设计者最初的设想。
一旦这种自我强化的循环开始,文化习惯很快就会变得根深蒂固且广泛传播,并且极难改变。志同道合的人会相互吸引。用户群体往往会吸引同质化的追随者。Visual Basic 的讲师倾向于传播他们的讲师所教给他们的东西。
正是这种对根深蒂固文化巨大惯性的认识,促使微软做出了保留 Visual Basic 并使其在语法层面几乎 100% 向后兼容的英明决策。他们认识到,试图让大批开发者放弃他们旧的文化规范并采纳新的方式是愚蠢的。
微软的英明之处不在于支持多种语言——如果真是这样,它肯定不会费心去搞 J#,因为 J# 在语法上与 C# 如此接近,仅为语言本身而支持 J# 是荒谬的。微软的英明之处在于支持多种文化。
具体而言
这在具体实践中意味着什么?这对今天的应用程序开发有什么影响?采用 Visual Basic 还是 C# 的决定如何影响今天和未来编写的程序?
- 80% 的 C# 程序员是优秀的,而 80% 的 VB 程序员则不是。这并非是说每个用 VB 编程的人都比每个用 C# 编程的人技术差。这是说:
- VB 的语法和语义旨在吸引技术水平较低的程序员,并且,结合上文探讨的其他因素,这创造了一种充斥着技术水平较低程序员的文化。
- 而且因为 VB 的语法和语义使得更难避免常见的编程错误,从而更难编写出好的程序。
- 雇佣一个好的 C# 程序员比雇佣一个好的 VB 程序员更容易。这是因为 (1)。
- 雇佣一个平均水平的 C# 程序员比雇佣一个平均水平的 VB 程序员成本更高。这是因为平均水平的 C# 程序员比平均水平的 VB 程序员更好,而这是因为 (1)。
- 雇佣一个好的 VB 程序员的成本与雇佣一个好的 C# 程序员相同。有很多好的 VB 程序员,其中一些比某些 C# 程序员要好得多。然而,这是例外,而非普遍规律。
- 一个优秀的程序员完成的工作量是一个普通程序员的二到十倍,并且造成的错误和麻烦要少 90%。
- 在撰写本文时,优秀的 VB 程序员数量可能与 C# 程序员数量几乎相当。这是因为 VB 程序员的总数远多于 C# 程序员。20% 的优秀 VB 程序员大约与 80% 的优秀 C# 程序员数量相同。
- 在不久的将来,优秀的 VB 程序员将少于 C# 程序员。这是因为许多优秀的 VB 程序员正在转向 C#。部分原因是他们更喜欢这门语言,但主要原因是他们更喜欢这种文化。随着文化差异变得更加明显和自我强化,这种趋势将会加速,直到剩下的优秀 VB 程序员寥寥无几。
- 平均而言,VB 程序员对优秀的面向对象、分布式、松耦合应用程序设计和开发的了解,要少于平均水平的 C# 程序员。这是因为他们的语言过去不支持这些概念,所以他们的文化是在没有这些概念的情况下成长起来的。尽管 VB 现在支持这些概念,但由于文化惯性,它们的采纳速度比在 C# 文化中要慢。
.NET 中文化的传播
在 .NET 框架下,VB 语言保留了支持现有(旧的)VB 文化的构造。这样做,当然是为了避免疏远该文化的成员。许多 VB 程序员仍在使用这些构造,尽管它们应该被避免。另一些构造本身无害,但它们继续在文化上强化一些习惯,包括那些有害的习惯。下面列出了一些关键差异的例子。这些只是例子,并非详尽列表。
- VB 默认允许后期绑定。虽然可以用
Option strict
关闭它,但文化使然,通常还是开着。这导致了许多难以捕捉的错误。C# 的绑定始终是早期的。 - VB 仍然支持旧的
On error goto
构造。这导致了草率或根本不存在的错误处理。C# 只支持更优越的try
…catch
错误处理。 - VB 支持可选参数。尽管 VB 开发者经常将此列为优点,但这实际上是一个缺点,因为使用可选参数会削弱调用者和方法之间的契约,让开发者可以放松分析,直到错误潜入才能发现。[注意:C# 的 param 数组构造与可选参数不同]
- VB 支持传统的 VB 函数,需要引用 Microsoft.VisualBasic.dll。这些函数中许多效率低下,都应该避免使用,转而使用 .NET 框架。然而,许多 VB 程序员仍在使用它们。在新的 VB 项目中,这个危险的命名空间是默认包含的。
- VB 允许用不同名称的方法实现接口,这使得查找实现变得混乱和困难。C# 不允许这样做。
- VB 支持后台编译。虽然这在小型项目中加快了开发周期,但在大型项目中会减慢 IDE 的速度,这至少在一定程度上导致了其文化倾向于小型项目。
- C# 的命名空间管理方式使程序员意识到命名空间及其重要性。而 VB 的命名空间管理方式默认将它们对程序员隐藏。对命名空间的细致管理是强大应用程序设计的基本原则,其重要性怎么强调都不过分。
结论
关于 Visual Basic 和 C# 的传统争论集中在功能差异上。由于这些差异微乎其微,因此有人认为选择 VB 还是 C# 应该取决于个人偏好。
这些论点没有考虑到 VB 和 C# 阵营之间深厚的文化差异。
事实是,虽然有一些杰出的 VB 团队编写出质量卓越的代码,但这只是例外,而非普遍现象。大多数 VB 团队在编写高质量代码方面都存在困难,这一特点深深植根于他们的文化之中,受制于他们无法控制的环境因素,并继续通过 Microsoft .NET 中的 VB 语法和语义得以传播。
因此:
- 如果一个组织满足于编写平均质量的软件,并且拥有平均水平的 VB 开发人员,那么转向 C# 可能没有任何好处。
- 如果一个组织拥有一支卓越的 VB 团队,并希望继续改进,那么继续使用 VB 存在真正的风险。风险在于程序员可能会为了 C# 的机会而离开。一旦有一位顶尖开发者这样做,团队向旧的 VB 文化倾斜的极化现象可能会加速,从而加速人员流失。
- 拥有卓越 VB 团队的组织应该转向 C#。卓越的 VB 团队学习新语法将毫无问题,所以没有风险。然后,该团队将在未来数年里从 C# 的语法、语义和文化中获益。
修订历史
- 2005年4月19日:修正了细微的语法错误,并删除了一个对广大读者无意义的我们公司内部项目的引用。澄清了几个可能被视为对 VB 开发人员不敬的部分,以表明问题不在于 VB 开发人员。问题在于该语言在特定环境背景下的成长历程……即它的文化。删除了关于 C# 额外好处的部分,因为它与本文的论点无关。
- 2005年4月19日:我向任何因本文感到或曾经感到被冒犯的人道歉。请仔细阅读。如果仔细阅读后您认为它冒犯了优秀的 VB 开发人员,请告诉我具体在何处/如何冒犯,我会修改文章。我的意图不是要冒犯任何优秀的开发人员,甚至不是一个正在努力的差劲开发者。批评那些导致一种文化让开发者难以变得优秀的因素……对此我毫无问题。
- 2005年4月22日:我收到了很多评论,说我说 C# 是比 VB 更好的语言(尽管我从未这样说过),所以我修改了第二段,以反映它们在功能上是等效的。
- 2005年5月10日:DotNetRocks 的 Carl Franklin 阅读了我的文章,并在最近一期的 DotNetRocks 节目中发表了评论,您可以在这里下载:.NET Rocks! - Kimberly Tripp on SQL Server 2005。作为 VB 的支持者,Carl 对这篇文章的评价相当负面。我对此本无异议,但我认为他也误解了要点,并试图通过断章取义来嘲笑这篇文章。但请您自行判断。我已将他的评论逐字记录在下面的评论区,您可以阅读、评论,当然也可以对他的评论进行评分。
- 2005年5月20日:一些发帖者要求我说明,本文,特别是关于 80/20 的评论,是基于我的个人观点,而非经验或统计数据。它们是我的观点。