【摘 要】Erlang語言是一種函數(shù)式語言,使用面向并發(fā)的編程方法。Erlang與分布式系統(tǒng)天性互相吻合,決定了使用Erlang開發(fā)分布式系統(tǒng)具有得天獨厚的優(yōu)勢。本文主要介紹了Erlang語言的來源和特性,以及如何使用Erlang進(jìn)行分布式編程,并分析了Erlang語言的應(yīng)用前景。
【關(guān)鍵詞】Erlang 分布式 并發(fā) 編程
一、引言
在計算機多核化發(fā)展日新月異、“云計算”“云存儲”異?;鸨慕裉欤恍┲髁髡Z言面向?qū)ο蟮某绦蛟O(shè)計語言(C++、JAVA、C#等)對并發(fā)和分布式程序的支持不是那么得心應(yīng)手。越來越多的鎖、信號量、線程、同步、互斥之類的概念讓程序日益復(fù)雜,出錯概率大增。
為了適應(yīng)并行計算和分布式應(yīng)用的大趨勢,Java 5.0引入了concurrency庫,C++有了標(biāo)準(zhǔn)化的OpenMP和MPI,微軟發(fā)布了Parrallel FX和MPI.NET等一系列產(chǎn)品。然而,這些亡羊補牢的手段卻不能彌補它們的“先天不足”——即這些語言在創(chuàng)作時就沒有把并行化的問題放到優(yōu)先的位置上去考慮。而天生面向并發(fā)的Erlang語言很好地解決了這個問題。
二、Erlang語言簡介
Erlang是一種“函數(shù)式語言(Functional programming,F(xiàn)P)”,使用的是面向并發(fā)編程(COP,Concurrency Oriented Programmi ng)的方法。
1987年,Erlang語言創(chuàng)始人Joe Armstrong在在愛立信做電話網(wǎng)絡(luò)方面的開發(fā)工作時,出于對高性能和并發(fā)的需求,在Prolog的基礎(chǔ)上增加了并發(fā)處理和錯誤恢復(fù),從而誕生了Erlang語言。
Erlang語言非常有特色,并發(fā)、分布、容錯貫穿于程序的始終,具有許多與其它語言不同的特性:
(一)跨平臺性
Erlang運行時環(huán)境是一個虛擬機,類似Java虛擬機,這樣的代碼一經(jīng)編譯,同樣可以隨處運行。當(dāng)然,如果你需要更高效的話,字節(jié)代碼也可以編譯成本地代碼運行。
(二)并發(fā)性
Erlang可以非??斓貏?chuàng)建和銷毀進(jìn)程,一個Erlang程序可以由多達(dá)幾百萬個超輕量級的進(jìn)程組成,這些進(jìn)程可以運行于單處理器、多核處理器或者處理器網(wǎng)絡(luò)上。Erlang進(jìn)程之間高度隔離,沒有共享任何數(shù)據(jù),只能通過消息傳遞來進(jìn)行交互,并且這種消息傳遞也是非常迅捷的。
消除了共享內(nèi)存以及進(jìn)程之間通過消息進(jìn)行通信是Erlang最明顯的優(yōu)勢之一,這一特點為進(jìn)行并行與分布式應(yīng)用的開發(fā)提供了非常好的基礎(chǔ)。
(三)分布式
Erlang被設(shè)計用于運行在分布式環(huán)境下。一個Erlang虛擬機作為一個Erlang節(jié)點。一個分布式Erlang系統(tǒng)是由多個Erlang節(jié)點組成的網(wǎng)絡(luò)。使用Erlang來編寫分布式應(yīng)用要簡單的多,因為它的分布式機制是透明的:對于程序來說并不知道自己是在分布式運行。
(四)健壯性
Erlang可以說是一門為健壯而生動語言。它不像其它語言一樣假設(shè)不會發(fā)生錯誤,而是假定錯誤隨時可能發(fā)生,并隨時準(zhǔn)備修正錯誤。
在一個分布式系統(tǒng)中,如果一個進(jìn)程出錯,讓這個進(jìn)程自己修復(fù)錯誤有時并不可行,有時節(jié)點可能徹底崩潰(死機),因此將錯誤交給其他進(jìn)程去處理是更恰當(dāng)?shù)倪x擇。
Erlang錯誤偵測的工作機制正是如此,通過進(jìn)程間的相互“鏈接”來實現(xiàn)進(jìn)程監(jiān)控(這些進(jìn)程可以運行于不同節(jié)點之上)機制,將錯誤進(jìn)行分層處理,從而實現(xiàn)構(gòu)造“容錯系統(tǒng)”。Erlang引入了“速錯(Fail fast)”的理念,在一個進(jìn)程出錯時不會試圖自行處理,而是直接退出,并發(fā)出錯誤消息讓其他進(jìn)程進(jìn)行錯誤處理、故障恢復(fù)等工作。
(五)軟實時性
Erlang支持可編程的“軟”實時系統(tǒng),這種系統(tǒng)需要反應(yīng)時間在毫秒級。而在這種系統(tǒng)中,長時間的垃圾收集(garbage collection)延遲是無法接受的,因此Erlang使用了遞增式垃圾收集技術(shù)。
(六)熱部署(Hot swap)
有些系統(tǒng)是不能夠由于軟件維護而停止運行的。Erlang允許程序代碼在系統(tǒng)運行中被修改。舊第代碼能被逐步淘汰而后被新代碼替換。在此過渡期間,新舊代碼是共存的。這也使得安裝bug補丁、系統(tǒng)升級而不干擾系統(tǒng)運行成為了可能。
(七)遞增式代碼裝載
用戶能夠控制代碼如何被裝載的細(xì)節(jié)。在嵌入式系統(tǒng)中,所有代碼通常是在啟動時就被完全裝載。而在開發(fā)系統(tǒng)中,代碼是按需裝載的,甚至在系統(tǒng)運行時被裝載的。如果測試到了未覆蓋的bug,那么只有具有bug的代碼需要被替換。
(八)外部接口
Erlang進(jìn)程與外部世界之間的通訊機制與Erlang進(jìn)程之間相同的消息傳送機制相同。這種機制被用于和操作系統(tǒng)通訊、與其它語言編寫的程序交互。如果出于高效率的需要,這種機制的一個特殊版本也允許例如C程序這樣的代碼直接鏈接到Erlang運行時系統(tǒng)中來。
三、Erlang語言的分布式編程
(一)分布式系統(tǒng)的特性
George Coulouris認(rèn)為:分布式系統(tǒng)是由位于網(wǎng)絡(luò)中的一些計算機組成的系統(tǒng),這些網(wǎng)絡(luò)中的計算機之間只能通過傳遞消息來進(jìn)行溝通和協(xié)調(diào)。Andrew S.Tanenbaum說:一個分布式系統(tǒng)是一些獨立計算機的集合,但是對這個系統(tǒng)的用戶來說,系統(tǒng)就像一臺計算機一樣。
盡管分布式系統(tǒng)還沒有一個公認(rèn)令人滿意的定義,但是所有分布式系統(tǒng)都有以下兩個特點:一、系統(tǒng)的各個節(jié)點(計算機)是相互獨立的;二、各個節(jié)點之間只能通過消息傳遞來進(jìn)行溝通和協(xié)調(diào)??梢钥吹剑植际较到y(tǒng)的這兩個特點也正是Erlang程序的特點:各進(jìn)程相互獨立,且只能通過消息傳遞來進(jìn)行交互。
Erlang與分布式系統(tǒng)天性互相吻合,決定了使用Erlang開發(fā)分布式系統(tǒng)具有得天獨厚的優(yōu)勢。Erlang天生面向并發(fā),在Erlang開發(fā)的分布式系統(tǒng)增加和刪除節(jié)點非常簡便,具有良好的伸縮性。
(二)Erlang語言分布式編程的兩種基本模型
1. 分布式Erlang
這種模型用于在一個緊密耦合的計算機集群上編寫程序,幾乎不需要額外操作,一切就像在單節(jié)點編程時一樣:可以在任何一個節(jié)點創(chuàng)建進(jìn)程,所有的消息傳遞和錯誤處理原語都可以照搬。分布式Erlang運行于一個可信任的環(huán)境中——因為任何節(jié)點都可以運行其他節(jié)點上的操作,這就需要一個高度信任的網(wǎng)絡(luò)環(huán)境。
2. 基于套接字的分布式應(yīng)用
使用TCP/IP套接字,可以編寫運行在非信任環(huán)境中的分布式應(yīng)用程序。這種編程模型的功能比分布式Erlang要弱一些,但是卻更加可靠。
四、Erlang語言應(yīng)用前景
Erlang已經(jīng)有二十多年歷史,利用它也成功地實現(xiàn)了一批項目,例如:Facebook用它重寫了超大型聊天系統(tǒng);Amazon用它開發(fā)了SimpleDB云存儲系統(tǒng);Yahoo!用它開發(fā)了Deliciou2.0……但是,Erlang迄今為止還是一門小眾語言。
Erlang至今未能廣泛應(yīng)用既有傳統(tǒng)程序員固有的面向?qū)ο缶幊趟季S難以適應(yīng)COP編程模式的原因,也有Erlang語言本身語法“怪異”,難以學(xué)習(xí)和理解等方面的原因。
除了Erlang,還有其它一些面向并發(fā)的編程語言,例如Scala、Go、F#等。這些語言各有特點,很難分出高下。盡管不能斷定Erlang是不是在并行領(lǐng)域是最優(yōu)的語言,但至少目前來說Erlang是比較好的選擇。Erlang憑借20多年的發(fā)展經(jīng)驗,在支持高并發(fā)、濃縮性和數(shù)據(jù)的持續(xù)性存儲都有相當(dāng)多的成熟庫(OTP)和開源軟件,使得它有極高的實用價值。此外,Erlang還有非?;钴S和成熟的社區(qū)為開發(fā)者解疑釋惑。
目前,隨著對高并發(fā)、分布部署、持續(xù)服務(wù)的需求日益增加,以及多核CPU的全面普及,Erlang必將得到越來越多廣泛的應(yīng)用。
參考文獻(xiàn):
[1]Armstrong Joe. Programming erlang [M]. Pragmatic Bookshelf, 2007.
[2]Armstrong Joe. A history of erlang [C]. Proceedings of the third ACM SIGPLAN conference on History of programming languages. ACM, 2007:6-1.
[3]Vinoski Steve. Concurrency and message passing in erlang [J]. 2012.
[4]Armstrong Joe, Virding Robert, Wikstr Claes, Williams Mike. Concurrent programming in erlang [J]. 1996.
[5]J?rleberg Anders, Nilsson Kim. Go, f# and erlang [J]. 2012.
[6]陳寅秋. Erlang——一種支持大規(guī)模并發(fā)處理的高可靠性編程語言 [J]. 電腦與電信, 2009, 11: 030.