Few languages have the mystique of Erlang, the concurrency language that makes hard things easy and easy things hard.

 

Erlang does seem to be gathering momentum because it solves the right problems in the right way at the right time.

 

"很少有像Erlang这样神奇的语言,作为一种面向并发的语言它把困难的事情变得如此容易,把容易的事情变得如此困难."《Seven Languages in Seven Weeks》的作者这样描述对Erlang的印象;《Seven Languages in Seven Weeks》这本小册子浮光掠影地介绍了7种语言,其中介绍Erlang的章节中,比较有料的是Joe Armstrong的访谈,和另外一篇访谈一起摘录于此,在这些访谈里面,我们不仅仅能读到技术:

 

Bruce: Why did you write Erlang?
Dr. Armstrong: By accident. I didn’t set out to invent a new programming language. At the time we wanted to find a better way of writing the control software for a telephone exchange. I started fiddling around withProlog. Prolog was fantastic but didn’t do exactly what I wanted. So, I started messing around with Prolog. I thought, “I wonder what would happen if I changed the way Prolog does things?” So, I wrote a Prolog meta-interpreter that added parallel processes to Prolog, and then I added error handling mechanisms, and so on. After a while, this set of changes to Prolog acquired a name, Erlang, and a new language was
born. Then more people joined the project, the language grew, we figured out how to compile it, we added more stuff and got some more users, and
. . . .


Bruce: What do you like about it the most?
Dr. Armstrong: The error handling and on-the-fly code upgrade mechanisms and the bit-level pattern matching. Error handling is one of the least understood parts of the language and the part where it most differs from other languages. The whole notion of “nondefensive” programming and “Let It Crash,” which is the mantra of Erlang programming, is completely the opposite of conventional practice, but it leads to r eal l y short and beautiful programs.

Bruce: What is a feature you most would want to change, if you could do it all over again? (Alternatively, you could answer, what are the greatest limitations of Erlang?)
Dr. Armstrong: This is a difficult question; I’d probably give different answers on different days of the week. It would be nice to add mobility to
the language so we could send computations over the Net. W e can do this in library code, but it’s not supported in the language. Right now I think it
would be r eal l y nice to go back to the roots of Erlang and add Prolog-like predicate logic to the language, a kind of new mixture of predicate logic
plus message passing.
Then there are a number of small changes that are desirable, adding hash maps, higher-order modules, and so on.
If I were to do it all over again, I’d probably give a lot more thought to how we fit things together, such as how we run big projects with lots
of code—how we manage versions of code, how we find things, how things evolve. When lots of code has been written, the programmer’s job

changes from writing fresh code to finding and integrating existing code, so finding things and fitting things together becomes increasingly impor-
tant. It would be nice to integrate ideas from things like GIT and Mercurial and type systems into the language itself so that we could understand
how code evolves in a controlled manner.


Bruce: What’s the most surprising place you’ve ever seen Erlang used in production?
Dr. Armstrong: W e l l , I wasn’t actually surprised since I knew this was going to happen.When I upgraded my version of Ubuntu to Karmic Koala,
I found a rather well-hidden Erlang ticking away in the background. This was to support CouchDB, which was also running live on my machine.
This kind of sneaked in Erlang under the radar to 10 million machines.

 

附另外一篇程序员杂志上的访谈:

Seibel:你是如何开始学习编程的?是从什么时候开始的?

Armstrong:是从中学时开始的。我出生于1950年,上中学那会儿还没有几台计算机。到了中学最后一年,那年我应该是17岁,我们当地的议会得到一台大型计算机,好像是IBM的。我们可以在上面写Fortran程序。通常,我们在编码纸上写好程序,然后发出去。一个星期后,等编码纸和穿孔卡拿回来的时候还必须确认一下。但是制作穿孔卡的人总会出点错,所以可能要反复1~2次才能弄好。最后这些穿孔卡就可以送到计算机中心了。

卡片进入计算机中心后会再拿回来,因为Fortran编译器会在程序中出现第一个句法错误的地方停下来,后面的程序就都不处理了。你的第一个程序似乎需要3个月才能跑通。我认识到,不能每次只送一个程序,应当并行地开发多个单一子例程并且一次都送去。我记得写过一个显示国际象棋棋盘的小程序,用打印机绘制出来。但是因为中间等待的时间太烦人了,我不得不把所有的子例程都当做并行的任务一次写完。

 

Seibel:你学的是物理学,是从什么时候开始转向编程的?

Armstrong:嗯,有一些本科生的课程需要编写程序,而我又特别喜欢编程。我还非常善于调试程序。如果别人程序出了问题,我就会去调试别人的程序。标准调试的开价是一杯啤酒。也可能提价,还有两杯啤酒、三杯啤酒的问题。

Seibel:在给他们调试程序时,是以他们必须给你买多少杯啤酒而论的,对吗?

Armstrong:对,等我修复了程序时他们要给我买啤酒。我在读程序的时候总是在想:“他们为什么要这样写程序呢,太复杂了。”我会重新编写并简化程序。看到人们编写复杂的代码我感到很吃惊。有些问题用几行代码就能解决,但是他们要写上几十行。我有点好奇,他们为什么看不到简单的方法呢。而我就颇为擅长采取简单的方法

我真正开始编程是拿到第一个学位并打算读博士学位的时候。我开始读高能物理博士学位并加入了那里的气泡室小组,他们有一台计算机。那是一台DDP-516,是Honeywell公司的。我可以独自一人使用它。它是穿孔卡式的,但是可以在上面直接运行程序,只要把穿孔卡放进去,按一下按钮,答案刷地一下就出来了。我特别喜欢那台计算机。我在上面编写了一个小象棋程序。

那时的实际磁心存储器是由妇女编织而成的,能够看到磁心和一块块的小磁铁和穿进穿出的线路。它的价格高得惊人,有一个大约10MB的磁盘驱动器,上面有20个小底板,大约15公斤重。它还配了一个电传文本的界面,可以在上面输入程序。

后来又出现了“玻璃电传打字终端”,那是最早的视频显示器设备,可以在上面输入并编辑程序。我觉得这太神奇了,再也不需要穿孔卡了。我记得当时和计算机管理员说:“要我说,将来有一天人人都会有这样一套机器。”他说道:“我看你疯了,Joe,你真是疯了!”“为什么不可能呢?”“这些东西贵得离谱。”

正是从那时我真正开始学习编程了。当时我的导师对我说:“你不应该再读物理学博士了,改行吧。你热爱计算机,应当搞计算机。”我说道:“不,不,不。我不能半途而废。”但实际上他的话是对的。

 

Seibel:那你拿到博士学位了吗?

Armstrong:没有。我没钱了,所以没有读完。我后来去了爱丁堡大学。此前在读物理的时候我们常常到物理系图书馆去学习。在图书馆的角落里有一些计算机科学书籍。有一些棕色封底的杂志叫做《机器智能》,一共有4期,是爱丁堡大学的机器智能系编辑出版的。我学的是物理学,但我却渴望阅读这些杂志,并且在想:“真是太有趣了。”DonaldMichie那时担任爱丁堡大学机器智能系的主任,我给他写了封信,说我对这种东西非常感兴趣,问他那里有没有工作可做。他给我回了信,说目前还没有,不过无论如何,他很想和我见一面,看看我是什么样的人。

几个月后我接到一个电话,也可能是一封信,是Michie的。他说:“我周二去伦敦,我们见一面如何?我要乘火车回爱丁堡,你能来车站吗?”我去了车站,见到Michie,他说:“嗯,不能在这儿面试—我们去找个酒吧。”于是我们到一家酒吧聊了聊。过了没多久又收到他的一封信,说:“在爱丁堡大学有一份研究工作,你申请一下吧。”于是我成了DonaldMichie的研究助理并去了爱丁堡大学。我就这样从物理学转到了计算机。

Michie在二战期间曾经和图灵在布莱切利公园(BletchleyPark)(编者注:二战爆发前,英国在距离伦敦不远的布莱切利公园设置了国家密码破译机构,许多破译员在那里工作,破解德国电报密码)一起工作过,拿到了图灵所有的论文。我在图灵图书馆有一张书桌,周围也全都是图灵的论文。我在爱丁堡大学待了一年。此后由于数学家JamesLighthill的原因,爱丁堡大学都有点维持不下去了。Lighthill受雇于政府,前往爱丁堡大学调查人工智能。他回去后说道:“那个地方什么有商业价值的东西也弄不出来。”

说得就像一个巨大的儿童游戏区。我是英国机器人学会的创始成员,我们都认为这个工作意义重大。但是拨款机构却说:“机器人!这是什么东西!我们不打算在这上面投入资金了。”我记得那是1972年前后,所有的资金来源都枯竭了,大家都说:“嗯,在这里度过的时光非常美好,但现在最好还是找点别的事情做吧。”

于是我又回去从事物理学工作了。我到了瑞典,在EISCAT科学协会得到一份物理学程序员的工作。我的上司来自IBM,年纪比我大,他想要上头给出一份规格说明书,这样他就可以拿去实行。我们曾经讨论过这个问题。他说:“如果没有任务说明,也没有规格说明,这样的工作太糟糕了。”我说:“嗯,如果没有任务说明,那才是一个好任务。因为你可以按照自己喜欢的方式来完成。”一年后我的上司离职了,我接替了他的工作,担任首席设计师。

我为他们设计了一个系统,可以称为应用操作系统,那是一个在普通操作系统上运行的系统。那个时候计算机的价格已经比较合理了。我们有一些NORD-10计算机,是挪威制造的—我觉得他们这种型号的计算机想要进入PDP-11的市场。

我在那里工作了将近4年。接着在瑞典空间研究中心得到一份工作,构建了另外一个应用操作系统,用于控制瑞典发射的名为“海盗”的第一颗卫星。那是一个有趣的项目,不过我忘了那台计算机的名字了,只记得它克隆的是Amdahl公司的计算机。那上面还只有行编辑器,没有全屏幕编辑器。所有的程序都只能放到一个目录下面。文件名是10个字母,扩展名是3个字母。还有一个Fortran编译器或汇编语言编译器,全部东西就是这些了。

有趣的是,现在回头想想,我不认为当今这些小玩意会让你的生产率更高。比如说分层文件系统,它怎么可能让生产率更高呢?很多程序开发方式是在脑海中形成的。我认为在那些简单的系统上工作可以强制你规范地进行思考。如果没有目录系统,就只能把所有的文件都放到一个目录下面,你只能变得相当规范。如果没有修订控制系统,你也只能变得相当规范。如果自己做的事情能够规范起来,那我觉得分层文件系统和修订控制系统也就没什么可取之处了。它们解决的问题并不能从本质上解决你的问题。如果多人一起工作,它们可能会让事情容易一些。但对个人来说,我看不出来有什么差别。

另外,我觉得我们现在因为选择过多而不堪重负。我的意思是,那时候我只能使用Fortran。甚至连Shell脚本也没有。只有可以运行程序的批处理文件,编译器,还有就是Fortran。如果确实需要的话,还可能有汇编语言编译器。不需要痛苦地做出选择。今天年轻的程序员肯定会感到很不舒服,面对20种编程语言和几十种框架,该如何选择,真是无所适从。我们那时没有这些难以选择的地方。只要开始做就行了,因为使用什么语言、什么工具都已经是定下来的。不需要考虑该做些什么,只管做就行了。

 

Seibel:另外一个差别是现在也无法彻底了解整个系统了。也就是说不仅仅是要做出很多选择,而且在选择要使用哪些黑盒的时候,还不一定完全理解黑盒的工作方式。

Armstrong:是啊,如果这些大黑盒不能正常工作,必须做出修改,我觉得自己把所有的内容都从头开始编写一次会更容易些。做不到软件复用,真是太糟糕了。

 

Seibel:但是如果把所有这些黑盒都打开,看看里面有什么,看看它们的工作方式,再确定如何对它们做一点改造来满足自己的需要。你觉得这样做确实是可行的吗?

Armstrong:这些年我犯了一些人们常犯的错误,那就是没有打开黑盒。有时候想一想,觉得这个黑盒无法理解,难度太大,所以不想打开它。我曾经打开过1~2个黑盒。有一次我需要做一个窗口系统,为Erlang做一个图形系统,我在想:“嗯,就在XWindows上运行吧。”XWindows是什么呢?它是一个套接字,上面跑着协议。只要打开套接字,往里面注入这些消息就可以了。为什么要用库呢?Erlang是基于消息的。整体指导思想是向其他东西发出消息,让它们执行操作。嗯,XWindows中的指导思想则是,有一个窗口,向窗口发送消息,再由窗口执行操作。如果在窗口中执行操作,它会把消息回送给你。这非常像Erlang。但是XWindows的编程方式是运用回调库—如果出现了这个情况就调用这个函数。这不是Erlang的思考方式。Erlang的思考方式是,给某个东西发送消息,让它做一些事情。所以,等一下,把其中的库去掉吧,直接和套接字对话。

猜猜结果会怎么样?非常简单。X协议收到了一些消息,我不知道具体是多少条,也许是100条、80条,大致就是这么多。但实际上只需要其中的20条就能完成有用的工作了。把这20条消息映射到Erlang术语上,变个小魔术,然后可以向窗口直接发送消息,它们就开始执行动作了。这样做的效率也很高。但界面不是很好,因为我没有把太多的精力用到图形和艺术标准上。如果为了让界面再美观一些,要做的工作还很多。但是不管怎么说,实际上并不难。

另外一个例子是我做的排版系统,我打开的抽象边界是PostScript。到了边界的地方你会想:“我不想越过这个边界。”因为你会认为边界里面的东西极其复杂。但是我再次发现,它实际上是很简单的。那是一种编程语言,一种不错的编程语言。抽象边界很容易穿越,而一旦穿越,会有很多收益。

在出版我那本Erlang编程书时,出版社说:“我们有画图工具。”但是画图工具真的很难精确地对准箭头,所以我不喜欢那些工具。而且画图的时候手也很难受。我想:“编写一个生成PostScript的程序,然后在‘这里画个圆圈、那里画个箭头’,让程序正常运转起来,这样一比,编程花的时间并不长。”编写程序需要几个小时。以所见即所得的方式画图也需要这么长时间。只是自己编写程序还有两个好处。你的手不会难受,而且即使把图形放大一万倍,看到的箭头也是对得整整齐齐的。

我并不是说刚入行的程序员应当把所有这些抽象的东西都打开。我的意思是,一定要考虑是否可以打开它们。不要完全放弃这个想法。看看直接到达的途径是不是比包装后的途径要快一些,这是值得一看的。一般来说,如果购买软件或是使用其他人的软件,一定要充分考虑还需要花很长时间来加工这套软件,因为它和你想要的不完全一样。软件的执行方式有微妙的差别,而这个差别可能需要很长时间来解决。

 

Seibel:同刚开始编程时相比,你在看待该如何编程的问题上最大的变化是什么?

Armstrong:我认为编程方式中的最大变化与硬件无关。显然,现在的计算机速度要快得多,功能要强大得多,但是人的大脑比最好的软件工具还要强大一百万倍。我在编写程序的时候,几天之后会突然说:“程序中有一个错误—如果这样、那样、那样、这样的话,程序就要崩溃了。”然后我去看了代码,确实如此。此前一点征兆也没有。你能告诉我哪一个开发系统能够做到这一点吗?作为一个程序员,我所发生的变化是内心思想的变化。

我认为在经过多年的编程之后会有两个变化。一个变化是,在年轻的时候,我会不停地写程序,直到完成。当程序完成后,我就不再管它了。程序写好了,完工了。然后我会突然领悟:“啊!搞错了!真是笨蛋!”我会重新编写程序,后来再次发现:“噢,程序是错的。”于是又重新编写。

我记得当时有这样一个想法:“先不要动手写代码,把这些东西都想好,这样做不是很好吗?”如果我不写代码就能获得那番领悟,不是很好吗?我认为现在可以做到这一点了。那20年可以算作是学习如何编程的时期。现在知道该如何编程了。我以前通过实验来学习编程。现在我知道该如何编程了,不需要再做实验了

偶尔,我也得做一些很小的实验,比如编写一些非常小的程序来回答某个问题。我会把事情想清楚,等到开始编程的时候,这些程序就可以或多或少地像我预计的那样运行起来了,因为之前我已经想清楚了。这也意味着要花很长时间。编写程序、有所醒悟、重新编写。这样可能需要花上一年的时间来写程序。所以我现在可能不这样做,而是先思考上一年。我不会再做那种简单的输入工作。

这是第一个变化。出现的第二个变化是直觉。在年轻的时候,我会通宵地写程序,干到凌晨4点钟,精疲力尽,那是男子汉气概的编程,一个小时接着一个小时,不停地编写代码。即使情况不好我也坚持不懈,总要让代码能够跑起来。即使没有直觉,我也要继续编程。

我得到的教训是,在疲惫的时候编写的程序都是垃圾,第二天就要把它们都扔掉了。20年前,就算强烈地感到事情不对劲、代码中有错误时,我也会继续编程。这些年来我注意到,真正好的代码是我完全进入状态的时候编写的,时间不知不觉地过了,而我甚至没有在考虑程序,只是很放松地坐在那里,输入这些东西,看着自己输入的东西出现在屏幕上。这样的代码会很不错。如果你不能集中注意力,弄出来的东西会说:“不行,不行,这儿错了,那儿也错了。”可我在多年前并没有注意到这一点。写出来的代码都被扔掉了。现在,如果觉得不行,我就不再编程了。“不能再写了。”这是我根据经验得到的,停下来,不要再写代码了。不要再处理这个问题了。干点别的。

我在上学的时候很擅长数学之类的课程,所以在想:“噢,我是一个按照逻辑思考的人。”但是我参加心理测试时,在直觉上得了高分,而逻辑思考方面的分数却有点低。不是很低,我还是可以做数学这类的题目,我相当擅长。但正是因为我擅长数学,所以我过去认为科学是关于逻辑和数学的。我现在就不会这样说了。我要说科学也有很多直觉,根据直觉能够知道什么是正确的。

Seibel:你现在在编码之前会花更长的时间思考,那么在思考阶段会做些什么呢?

Armstrong:噢,我会记些笔记,我不仅仅是在思考。在纸上随便写点什么。我可能不会写很多代码。如果你密切注意我的活动,会发现我大部分时间都在思考,偶尔写点什么。另外一件对解决问题非常重要的事情是问问我的同事:“你将如何解决这个问题?”你找到他们,说:“我不知道应当采取这种方式还是那种方式。必须在A和B之间做出选择。”然后你向他们描述A和B,等讲到一半的时候,你会说:“啊,是B。谢谢你们。非常感谢。”这样的事情发生过很多次。

你需要这样一块智能白板,如果你只是独自一人在一块白板上写写画画,是得不到反馈的。但是如果面对的是人,你会在白板上向他们解释替代方案,他们也会加入讨论,提出一点建议。然后突然间你就知道答案是什么了。对我来说没有涉及到代码编写。但是和处理同样问题的同事进行交谈是非常有价值的。