InfoQ

文章

什么是Ruby之道?

作者 Hal Fulton译者 董彬 发布于 2007年10月6日 下午7时28分

社区
Ruby
主题
编程
标签
图书

作者Hal Fulton刚刚更新了他的经典之作——The Ruby Way《Ruby之道》,已由人民邮电出版社出版Hal之所以要这么做的原因是由于十月第三周要赶上 RubyConf 2006并且要配合着Addison Wesley专业Ruby系列图书的启动。在这次InfoQ的独家采访中,Hal回答了贯穿整本书的问题:

相关厂商内容

活动:体验基于OpenSolaris的Web/企业应用(8.30 杭州)

Ruby的开放类──或者:怎样避免动态打补丁

SOY Framework:Java富客户端快速开发框架

互联网开放平台技术趋势和讨论

免费迷你书下载:Grails入门指南

相关赞助商

InfoQ中文站Ruby社区,面向Web和企业开发的Ruby,主要关注Ruby on Rails,通过新闻、文章、视频访谈和演讲以及迷你书等为中国Ruby社区提供一流资讯。

什么是Ruby之道?

Let us prepare to grapple with the ineffable itself, and see if we may not eff it after all.

让我们时刻准备着向那些所不能说的挑战,看看最终是不是可以说。

——摘自Douglas Adams的作品Dirk Gently’s Holistic Detective Agency

我们所说的”Ruby Way“是什么意思? 我认为有两个相关方面: 一个是ruby的设计哲学; 另一个是它的使用哲学. 设计和是使用相关这是自然的事情, 无论硬件还是软件; 否则生物工程学如何产生? 如果我制造了一个设备并且在上面装了一个把手, 那是因为我希望别人可以通过把手使用这个设备.

Ruby有一种难以名状的品质让其与众不同。我们可以从这门语言的语法和语义上,也可以从用Ruby编写的代码中窥豹一斑。但一旦我们辨别了其中品质,我们就知道怎么回事了。很明显Ruby不只是创造软件的工具,而且是一种有主见的软件。为什么Ruby程序的使用原则不同于Ruby语言本身的使用原则?毕竟Ruby是高度动态和可扩展的。这两种层次的Ruby用法有所不同,原因可能是现实世界的不协调性。但总而言之,思想过程应该是一样的。Ruby语言可以通过Ruby来实现,用Hofstadter风格,虽然本文撰写时尚无例证。

我们不常想到”Way“这个词的本义;但是它被赋予两个重要涵义。一方面,它意为方法或者技术,但它也意为道路或途径。显然这两种意思是相关的,而且当我说“Ruby之道”的时候,两种意思都有。

所以我们我们所讨论的不仅是一种思考过程,而且是我们追随的一种做事方式。即使最伟大的软件领袖也不能宣称达成完美,而只是追随着完美主义。而且世间做事的方式不止一种,但我只能讨论一种。传统智者说:形态取决于机能。而且传统智者当然通常是正确的。但是Frank Lloyd Wright (在自己的领域)曾经说过:“形态取决于机能——已经被曲解了。形态和机能本为同一物,源于自性本体。”

Wright所说何意?我想他想表达的意思是真理不是你从书本上学到的东西,而是从经验中修证而来。

但是我以为Wright表达的真理在某些方面易于理解。他是一个伟大的简单性倡导者,他曾说过:“一个建筑师最有用的工具是草图板上的橡皮擦。”

所以Ruby美德之一是简单性。我可以在此主题上引用其他思想家的话么?按照 Antoine de St. Exupery的说法,“完美之道不在于无可添加,而在于无可剔除。”

但是Ruby是一门复杂的语言。我怎能说它简单呢?

如果我们更好地理解了宇宙,我们可能找到一种“复杂性的永恒法则”——一个现实中扰乱我们生活的事实,例如熵,以至于我们不能逃避,只能改变其分布。

而且这就是关键。我们不能逃避复杂性,但是我们能把它推到一边。我们能将其埋葬于视野之外。这就是工作中古老的黑盒原则;一个黑盒执行一个复杂任务,但是从外面看它具有简单性。

如果你还有耐心来听我引述,爱因斯坦的一句话此处非常适合:“任何事物都应简单到极致,而非更简单。”

所以从Ruby中我们看到了从程序员视角诠释的简单性(如果不是从Ruby解释器维护者的角度来看)。但是我们也看到了妥协所导致的特性。现实世界中,我们必须妥协一点。例如Ruby程序中的每一个实体必须是一个真的对象,但是某些值比如整数型是直接存储的。为了让计算机系学生感觉更亲切,我们已经牺牲了一些优雅的设计来达成实现的可行性。实际上,我们牺牲了一种简单性来换取另一种简单性。

Larry Wall关于Perl所说的话仍适用于此:“当你用小型的语言说话时,话会很冗长。当你用大型语言说话时,话会很简短。” 英语同样如此。生物学家Ernst Haeckel可以用三个词说出“Ontogeny recapitulates phylogeny”是因为他可以支配这些针对特定语义的强大词汇。我们允许语言的内在复杂性,因为这使得我们把复杂性从每个个体的表达中移走。
我想这样表达这条原则:不要写200行代码,如果10行可以搞定。

我理所当然地认为简洁是一个好东西。短程序段将占据程序员更少的大脑空间;作为独立实体,它将更易于理解。作为一个令人愉快的副作用,这种代码编写的时候,能钻进来的bug更少。

当然我们必须牢记爱因斯坦关于简单性的告诫。如果我们赋予简洁太高的优先级,我们终将无可奈何地陷入令人困惑的代码之中。信息理论告诉我们,压缩数据统计上接近于随机噪音;如果你看过C,APL或者正则表达式的标记法--尤其是写得很糟糕的--你已经直接地经历了这个事实。“简单,但不要太简单”;这就是关键。拥抱简洁,但不要牺牲可读性。

众所周知,简洁和可读性都好。但有一个深层次原因,它太根本了以至于我们时常把它忽略。这个原因是计算机为人而存在,反之不然。

过去的日子里,情况几乎相反。计算机耗费了数百万美元并且吃掉了上千瓦的电。人类表现得好像计算机是一个神,而程序员是卑贱的附属品。计算机一个小时的开销要比人一个小时大得多。当计算机变得更小和更便宜,高级语言也变得越来越流行。它们从计算机的角度看是低效的,但是从人的角度来看是高效的。Ruby简直是一个你怎么想就怎么写代码的语言。有些人实际上称之为VHLL(Very High-Level Language);虽然这个术语没有好好定义,我想它用在这里正合适。

计算机应该是仆人,而不是主人,而且如Matz所说,聪明的仆人应该通过几条简短的命令就能完成复杂的任务。整个计算机科学的历史中,这已经成为了真理。我们从机器语言开始,然后进化到汇编语言,之后步入高级语言。

我们这里讨论的是一个从以机器为中心的语法转移到以人为中心。依我看来,Ruby是一种人本主义编程的优秀典型。

我想岔一下话题。有一本80年代出版的小书叫做《编程之道》。书中字字珠玑,但是我只想复述这句:“程序应该符合'最小惊异原则'。这是什么原则?简单地说就是程序应该以让用户惊异最小的方式响应用户。“(当让对于语言解释器来说,用户就是程序员。)

我不知道是不是James铸就了这条格言,但是他的书使我第一次了解到这段话。这是一条在Ruby社区广为人知并且频繁引用的原则,虽然通常被称为最小诧异原则或者POLS(本人更喜欢LOLA)。

无论你怎么称呼它,这条规则很有效,并且成为了整个Ruby语言的开发的指导原则。这也是开发Ruby库或者用户接口的指导原则。

唯一的问题当然是不同的人所诧异的事不一样。对象或者方法“应该”如何行为没有统一的共识。我们可以尽力争取一致性,争取证明我们的设计决策,而且每个人能够训练自己的直觉。

对于此问题,Matz说过“最小诧异”应该指的是他自己是设计者。你的想法和他越接近,Ruby让你诧异越小。并且我向你保证,效仿Matz对于我们大多数人来说不是坏主意。

无论一个系统从逻辑上如何构建,你的直觉都需要学习。每一门编程语言都是自己的世界,基于自己的一系列假设,自然语言亦是如此。当我学德语时,我得知所有名词都要大写,除了deutsch。我对教授抱怨,毕竟这是语言的名字,不是么?他笑着说,别跟它打架。

他教我的是让德语是德语。延伸来讲,这是对于从其他语言转到Ruby的金玉良言。让RubyRuby。别让它成为Perl,因为它不是;不要让他成为LISP或者Smalltalk,同样不是。另一方面,Ruby具有这三门语言的的共性。跟随我们的期望来开始,但是与其相左时,别跟它打架。(如果Matz不同意这个改变是必要的)

今天每个程序员都知道正交原则(更好的术语是“正交完备性”原则)。假设我们有一对坐标轴,一根轴定义了一系列可以比较的语言实体,另一跟轴有一些属性或者特性。当我们说正交,我们通常指这两个轴所定义的空间和我们逻辑上定义的一样完整。

部分The Ruby Way是争取正交性。Array某些方面和Hash类似;所以对他们的操作也应该类似。当进入他们行为不同的领域时,操作才不一样。

Matz说“自然性”通过正交性来评估。但是如何理解什么是自然性或者什么不是可能需要一些思考和编码。Ruby争取对程序员友好。例如,许多方法有别名,并且都返回数组的实体个数。变体指向同一个方法。有些人认为这是一个令人困惑的或者坏的特性,但是我认为这是一个好设计。

Ruby争取一致性和规律性。这点没有任何神秘的;生活中的每一方面,我们都渴望事物是有规律和对等的。机敏的是学会何时违反这些原则。

例如,Ruby习惯在预测行为的方法名后面加个问号“?”。这点不错,它让代码清楚,让命名空间更易于管理。但是更有争议的是类似的惊叹号“!”的用法,标明方法具有破坏性和危险性,从它们修改了接受者这个意义上。争论起源于并非所有破坏性的方法都通过这种方式标注。我们不应该保持一致性么?

不,实际上我们不该。一些方法很自然地改变接受者,例如replace方法和允许给类属性赋值的”writer”方法;我们不应该为每一个等号赋值的后面都加一个惊叹号。一些方法有争议地改变接受者的状态,这种情况太频繁,以至于不能用这种方式标记。如果每个破坏性的方法都以“!”结尾,我们的程序很快就会像多级市场公司的销售手册一样。

你注意到相反力之间的张力了么,一种违反所有规律的趋势。让我用Fulton第二定律来陈述它:所有规则都有例外,除了Fulton第二定律。我们在Ruby里看到的不是一种“愚蠢的一致性”,也不是一系列简单规则的刻意坚持。实际上,The Ruby Way的部分是它不是一个僵化,不灵活的方式。在语言设计中,Matz曾经说过,你应该“跟随你的心(follow your heart)”。但Ruby哲学的另一方面是:不要害怕运行时的变化;不要害怕动态性。这个世界是动态的;为什么编程语言应该是静态的?Ruby是现存最动态的语言之一。

我想据理力争的另一方面是:不要成为性能问题的奴隶。当性能不可接受时,这个问题一定会被处理,但通常它不应该是你考虑的首要问题。宁要优雅不要效率,在效率不是关键的地方。如果你正在写一个可能以不可预料的方式运行的库,性能可能从一开始就是关键。

当我观察Ruby,对于一个复杂的物理学上n-body回忆者问题,我觉察到了不同设计目标的一种平衡。我可以想象它可以建模为Alexander Calder Mobile。这可能是交互自身,其具体表现Ruby哲学而不是独立的部分。程序员知道他们的手艺不只是科学和技术,而是艺术。我不愿说计算机科学中有宗教思想,但就你我之间,确实存在。(如果你还没有读Robert Prisig的《禅与摩托车修理技术》Zen and the Art of Motorcycle Maintenance,我建议你读一读)

Ruby从人类力求创造实用并且美好的事物中诞生。用Ruby写的程序应该源于同一天赐本源。此本源,对我来说,便是The Ruby Way之本质。

关于作者

Hal Fulton 拥有Mississippi大学的两个计算机学位。在因为一些工作(主要是IBM Austin)搬家到得克萨斯州Austin之前,他在地区技术院校教了四年计算机科学。他在各种形式的UNIX上工作过15年,包括AIXSolaris,和Linux。他1999年接触了Ruby,并且2001年开始撰写这本书的第一版,这是英语的第二本Ruby书。他参加过6Ruby大会,并且在其中4次做过演讲。包括在Karlsruhe, Germany 的第一次欧洲Ruby大会。他现在AustinBroadwing Communications,致力于大型数据仓库和相关通讯应用。他的日常工作使用C++Oracle,当然也包括Ruby

Hal仍旧活跃于Ruby邮件列表和IRC频道中,并且有几个开发中的Ruby项目。他是ACMIEEE计算机协会的成员之一。个人生活中,他喜欢音乐,读书,写作,艺术,和摄影。他是火星协会的会员之一,并且是一名太空爱好者,他希望在有生之年步入太空。他住在得克萨斯州的Austin

查看英文原文:What is the Ruby Way?
译者简介:董彬,NibiruTech创始人之一,现致力于运用Ruby on Rails等高端技术和敏捷过程为客户提供项目定制和咨询服务。他曾效力于IBM 中国开发中心,对于企业应用开发具有丰富的经验。个人爱好是户外运动和围棋。他的blog地址是:http://dongbin.javaeye.com/

2 条回复

回复

快看完了 发表人 Jerome Chen 发表于 2007年11月29日 上午1时4分
Re: 快看完了 发表人 Jerome Chen 发表于 2007年12月11日 下午7时38分
  1. 返回顶部

    快看完了

    2007年11月29日 上午1时4分 发表人 Jerome Chen

    整体感觉上还是非常不错的,不过有的术语翻译不是特别好。 可能是我悟性太差吧,还是没有看出“道”来,呵呵。 ------------------------------------------ [Ruby中文社区] - ruby-lang.org.cn

  2. 返回顶部

    Re: 快看完了

    2007年12月11日 下午7时38分 发表人 Jerome Chen

    update: 已经看完了,呵呵。感觉还是有些沉淀的。不错的book. ------------------------------------------------- [Ruby中文社区] - www.ruby-lang.org.cn

独家内容

利用Ruby简化你的Java测试

本文是Productive Java with Ruby系列文章的第一篇,我将从单元测试这个话题开始,让Java的开发人员能够在实际工作中利用Ruby提高工作效率。

与赵进聊SaaS

InfoQ中文站有幸与阿里软件的首席架构师赵进在一起探讨了SaaS的相关话题,包括SOA和ASP与SaaS的异同、云计算、SaaS的前景、它的关键技术、技术瓶颈等等。

在ESB中选择路由还是编配?

在这篇文章中,Adrien Louis和Marc Dutoo在一个典型的ESB场景中讨论了编配和路由的区别和优缺点。他们讨论了几种连接服务的方法,从使用如自定义路由这样的低级别方法,到使用如工作流和编配这样面向业务的高级别方式,并总结说不存在“一边倒”的解决方案。

分布式系统中的一致性和可用性

本文是根据7月26日InfoQ中文站在杭州举行的QClub活动(第三期)后半程小组讨论总结而成。主要内容包括如何在SOA系统中实现服务编排,如何保证分布式系统中的一致性和可用性,以及如何在实施SOA的过程中控制接口的粒度等。

虚拟化导论

人们很容易想当然的以为虚拟化技术仅仅应用于服务器。而在现实中,虚拟化这一苏醒的概念正被运用于各个层面,其中包括网络,存储以及应用基础架构。在这篇导论中,InfoQ将深入每个方面,详尽向您描述虚拟化技术的运用以及其优点与不足。

用户故事估算技巧

作为开发者,同时也是ThoughtWorks的咨询师,Jay Fields总结了自己估算用户故事的有效技巧。

InfoQ案例研究:纳斯达克市场回放

在这篇案例研究中,InfoQ对Adobe AIR和Amazon的简单存储服务(Simple Storage Service ,S3)在NASDAQ市场回放程序(NASDAQ Market Replay)中的应用进行了详细的分析。

Hadoop基本流程与应用开发

本文介绍了Hadoop的基本流程、业务场景、代码范例以及集成测试。本文是《分布式计算开源框架Hadoop入门实践》三部曲的最后一部。