一張主流編程語言的變遷圖,講清程序員遷移模式

【文章來源微信公眾號:每天學編程】

關于編程語言,還有很多類似的圖可以表示它們相互之間的演進。不過我并不想從語言設計者角度來說明這個問題,而是想從程序員本身來看待語言演變。雖然兩者間有些接近,但并不完全相同。

從該圖可以看出,如果開始使用的是編程語言 A,下一個最有可能切換過去的是哪種語言。這種推測不是非常科學。不過如果你需要精確的科學,就不會在這里閱讀這篇文章了,對嗎?也許這張流程圖對我來說,能揭示更多的內容。

聲明:在此處,不考慮程序員最喜歡的是什么語言。人們可以在任意兩個語言之間切換,也可以學習很多種語言、然后選擇最適合工作的一種語言。本文中的觀點有一定的傾向性。

在接下來的篇幅里,我所闡述的均為個人觀點。為了不影響讀者閱讀,就不再一一做出聲明了。

我想強調下最普遍的“終極節點”。在這些節點上,人們在他們所處的維度找不到更好的可替代編程語言。這些終極節點包括:Rust、 Java、 Go、 Python 3、Javascript 和 node.js(node.js 作為一種特殊的 Javascript,在這里特別指出)。

幾年前,我認為 C 也是一個終極節點。可能現在也還可以這樣認為,因為有大量的重要項目(如 OS 內核)仍使用了 C,而且可以認為它無可替代。不過有跡象表明 C 其實是可以替代的。我最喜歡的例子就是有趣的空指針。Linux 內核有個編譯器帶來的致命弱點,即 NULL 值“不可能”出現,因此沒有對函數進行空指針檢查。C 也是一團糟,其規格里有幾個新編程語言所沒有的致命錯誤。也許某天這些錯誤能被修復。

讓我們回退幾步。如果從頂部開始,根據人們進入編程的不同規格,可以看到四個主干:

  1. “低級”編程,包括 asm 和 C。
  2. “商業型”或“學習型”編程,從 BASIC 開始。
  3. 計算類 / 科技類編程,如 Fortran,MATLAB 和 R。
  4. 腳本 / 膠水編程,如 shell 和 perl。

(我們也會談到“數據庫查詢語言”,比如 SQL。它是一枝獨秀,所有替代它的嘗試都以失敗告終。數據庫語言從上世紀六十年代開始就停滯不前了。甚至到現在,其關鍵字仍使用大寫,因為(他們認為)這樣能更好的理解代碼。)

(我還忽略了 HTML 和 CSS。他們是真正的語言,不過現在大家都開始學習這兩種語言,圖上無法用相應的箭頭來標識。Lisp 也沒有考慮在內,因為它一直沒有流行過,雖然有一小部分人一直希望它能流行起來。我還建議添加第五個分類,“配置編輯”)

(該圖也忽略了 Haskell。它可以在旁邊用一個獨立的框來表示,和其他語言之間沒有出入的箭頭,不過這沒關系。Haskell 是個自嘲式的大笑話,除非涉及到 Monads,它不再使用 I/O 概念。)

不管怎么樣,讓我們回到上世紀九十年代。假設那時編程世界很簡單,(1) 初級程序員使用 C,asm 或者 Turbo Pascal,(2) 商業程序員使用 VB,(3) 數值計算人員使用 Fortran,R 或 MATLAB,(4) 膠水編程者使用 sh 或 perl。

那時,編程語言就是這么嚴格劃分的。畫該圖時,我才意識到這一點。顯然,我們不會用 perl 來寫操作系統內核,不會用 MATLAB 來寫膠水程序,不會用 VB 來寫大型矩陣相乘算法。

現在則變化很大。選擇什么樣的語言已經不再像過去那樣明確了。

語言的變化主要是風格的變化

我們先來看樹起點 asm(匯編語言)。用 Asm 來寫程序是相當困難的。不過即使到現在,它仍是寫某些程序最好的方式(如電腦啟動后的最初幾個指令,或是中斷處理的入口代碼)。不管是在 App Store 里還是手機上的 JIT 里,每個編譯語言最終都會將代碼編譯成匯編或機器語言。

基于 asm,出現了兩個分支:C 類型分支和 Pacal 類型分支。(Algol 出現的更早,不過此處忽略掉。宣稱自己是 Algol 程序員的人并不多。Algol 對其他語言影響很大。)

Pascal 風格分支語言的特點是有 “begin…end”。C 風格語言的特點則是有括號。當然,C 影響了很多的編程語言設計,這點在圖中沒有體現。因為我們現在討論的是程序員,而不是語言設計人員。

首先來看看 C。很奇怪,一旦人們開始使用 C,就習慣用它來處理各種情況。不管實現優劣與否,它是為數不多的能合理實現所有四類編程問題的語言之一。這四類都有些難度(除了低級編程,它正是 C 擅長的領域),不過 C 都能搞定,速度也還可以。

如果你是個 C 程序員,接下來會使用那種語言呢?這取決于用它來做什么。

顯然,C++ 是一個選擇。雖然其名字與語法和 C 很像,但它其實和 C 風格迥異。除了 BeOS,其他操作系統內核不會使用 C++。在極具潛力的 Rust 使用前,操作系統基本都使用 C 編寫。

但是商業(“大型程序”)和數值計算(“快速程序”)領域的人員喜歡 C++。說喜歡不一定準確,但他們別無選擇,只能使用 C++。

對于膠水程序,很多人會直接從 C(或 C++)轉到 python 2。我最近也這樣做過。和怪異的 perl 不同,Python 2 類似 C 語言風格,其語法更簡單。C 程序員很容易理解 python C 模塊(并可以編寫新的 python 模塊)。從 python 里調用 C 函數比其他語言更簡單。如果在 Java 里調用,就需要處理非引用計數的垃圾回收問題。python 的“os”模塊提供了 C 系統調用及該調用能工作的環境。程序員可以訪問 C 語言中的錯誤碼并設置相應信號處理程序。唯一的問題就是 python 有些慢。不過只把它作為膠水語言,則可以不考慮 python 的慢速。速度慢時,可以寫 C 模塊或調用 C 的庫或子程序。

另外,Java 面世后,很多 C 和 C++ 商業軟件的程序員非常快地切換到 Java。C++ 編譯時間長,頭文件繁多,可移植性差,有釋放后重用的錯誤問題。因此,雖然 Java 運行的很慢(和 python 不同的是,Java 宣稱“理論上運行很快”),人們還是更愿意使用 Java。

我記得有篇文章講過,Go 的設計者最開始認為 Go 可以和 Java 或 C++ 媲美,但實際沒有做到。Java 就像知名酒店,或是門洛帕克(Menlo Park),一旦入住就不想離店。同時,程序員沒有從 C++ 切換到 Java 主要是因為:a)Java 速度比 C++ 慢,b)Java 仍有垃圾回收的經典問題。

Go 在之前已經切換到 python 2 的膠水程序人員中流行起來。事實證明 python 的慢速是其痛點所在。計算機復雜度急劇增加,python 膠水程序規模也越來越大。相較其優勢,動態類型帶來的麻煩更多,因此人們開始使用預編譯二進制。python 2 占用很多內存,因此 Go 做了 RAM 改進,避免了從 C++ 遷移到 Go 帶來的問題。Go 的難度和 python 差不多,但它運行更快,占用 RAM 更少。

我們現在稱 Go 是一種“系統”語言,因為提起膠水程序,我們更多的是想到 perl 和 ruby,不過它們的作用是一樣的。(試試告訴一個 C 語言內核開發者,Go 是“系統”語言,看看他們的反應)Go 是粘合劑,可以把各個組件組合到一起成為一個系統。

Hejlsberg 因素

我們接下來看 Visual Basic 和 Pascal 分支。人們有不同的想法:明顯正確的(“我為什么會使用與 C 或 Java 一樣讓人痛苦的語言呢?”),或明顯錯誤的(“可視化的…Basic?開玩笑吧?”)。二十世紀八十年代和九十年代,一些人仍認為編程應該讓新手可以方便使用,因此在個人電腦上預裝了免費的編程語言,大部分都是 BASIC。

另一方面,大學教授編程時,則避開了 BASIC[“如果學生前期使用過 BASIC,就不能對學生很好的進行編程授課”,也沒有選擇 C。他們更傾向于 Pascal,認為 Pascal 易于學習。就像 Algol 的學術論文里提到的一樣,而且它的語法適合教學,能讓每個學生都能聽懂。因此就有了學術分支和個人電腦分支,不過它們有個共同點,那就是都和 C 不像。

基于 PC(DOS)的 BASIC 演變為基于 Windows 的 Visual Basic,這可能是 javascript 出現前使用最多、最受歡迎的編程語言。(現在,它仍是在 Excel 中使用的“宏”語言。目前有很多 Excel 的程序員,雖然他們并不認為自己是程序員。)

同時,Pascal 也在努力往 PC 轉。因為 Turbo Pascal 的出現,它變得流行起來,并一度成為最快的編譯器。在速度上,Pascal 的確沒有夸張。甚至有一些 C 程序員也喜歡用 Pascal,不是因為喜歡其類 C 的語法,而是因為它的速度很快。(Turbo C 也可以,但速度還不夠。它比其他 C 編譯器都快。)(大學里,Pascal 學術性越來越強,后來演變成 Modula 和 Ada。如果不是美國軍方在其高可靠系統中采用了 Ada 語言,這個分支早該終結了。現在我們可以忽略 Ada。)

那時還有兩個“商業”開發分支:BASIC 和 Pascal 分支。Windows 問世后,出現了 Visual Basic。基于 DOS 的 Turbo Pascal 有點過時,基于 WIndows 的 Turbo Pascal 也并不出眾。為了競爭,Turbo Pascal 的設計者Anders Hejlsberg創建了 Delphi。Delphi 和 Visual Basic 一樣,有可視化的編程環境,但它基于 Turbo Pascal 語言,也極少出現找不到或不匹配實時動態鏈接庫的煩人問題。

Delphi 很好,但它不屬于 Microsoft。摻雜商業因素后,局面變得有些困難。在一系列出人意料的事件之后,Hejlsberg 離開了 Microsoft,但仍繼續 C# 的開發,發布了 Microsoft .NET 平臺,并包含 Visual Basic.Net。據稱 C# 統一了兩個分支。

不幸的是如前所述,VB.NET 很可怕。它和 Visual Basic 幾乎沒有共同點,更像是 C++ 的一個慢速版本,披了件有點非典型 Basic 的語法外衣,還帶著一個更糟的 UI 設計工具。C# 也不是 Delphi。不過這幾種語言都銷聲匿跡了,Microsoft 盡力推動了這一點。(除了 Microsoft Office,它到現在仍在使用最開始的 Visual Basic 語法,稱為 “Visual Basic for Applications”, 即 VBA。比起.NET,它使用的更廣泛,更受用戶喜歡。)

我不清楚怎樣才能叫做一名 Visual Basic 程序員。微軟致力于讓他們改用 VB.NET,但大多數人并不愿意。我想在圖中畫一條“他們實際的選擇”的箭頭,不過老實說我也不知道應該指向哪里。也許他們成為了 web 開發者,或者編寫了 Excel 的宏。

從現在看,如果寫基于微軟主推的基于.NET 平臺的 Windows 軟件,是件很有趣的事。可能使用的語言都會深受 Hejlsberg 的影響。Hejlsberg 的語言在反擊之前被微軟和 Visual Basic 所遏制,于是 Hejlsberg 轉向寫 Typescript,這個留待以后討論。

膠水語言的簡要介紹

最初的膠水語言是 Unix shell,它因引入“管道”概念也很著名。“管道”連接簡便的工具來完成復雜的工作。

事實證明,設計小而簡單的工具是困難的,通常我們沒有足夠的時間來做這個。能夠讓我們跳過這些輕便工具,致力于編寫奇特的、能夠粘著很多亂七八糟的小程序的語言變得越來越流行。(它對 shell 語言的缺陷,尤其是與引用和通配符擴展規則相關的缺陷并沒有幫助。)

第一個是 awk,它是語法和 C 類似的解析語言,可以用在 shell 的管道上。那時,在一種語言(sh)的一行中里使用另一種微語言(awk)有點奇怪,慶幸的是我們適應了,因為現在的 web 程序都是這樣的。(我們略過 csh,它是另一種與 C 語法不兼容的語言,存在不同的致命缺陷,可以被 sh 替代。)

接下來是 Perl。awk 沒有足夠多的標點符號,從而促成了 Perl 的產生。(好吧,這只是個玩笑。)

Perl 開始到 perl 5,越來越受歡迎。現在,Perl 停止改進語法,在 perl 6 上傾盡全力,從零開始打造。(在圖中并沒有標出 perl 6,因為還沒有人切換過去。)

這樣的配置給在幾個方向斷層進行“粘合”留下了空間。如果程序員覺得 perl 的語法差勁,可能會切換到 python。如果他們認為 perl 的語法很神奇有效力,只需要一些調整,則可能會切換到 ruby。如果使用 perl 來運行 web 的 CGI 腳本,則可能會保持原樣,也可能會轉而切換到 PHP。

ruby 很快成為 web 服務器支持的語言(進而是 Ruby on Rails)。Python 也同樣在演進。

現在有趣的是:整整一代程序員摒棄了命令行方式(這也是膠水語言運行的方式),希望在 web 端可以做任何事情。從某方面來說,這樣更好,比如在一個膠水程序中可以超鏈接到另一個膠水程序。從另一方面來說,則更糟糕,因為現在所有的 web 程序都很慢,不能使用腳本,而且安裝 Electron 的另一個副本需要 500MB 的 RAM 空間等等。這就引入了 web 語言這個話題。

Web 語言

圖中,集中在 javascript 的“膠水”分支有很多的箭頭指向,這并不奇怪。Javascript 最初只使用于前端。當 node.js 出現后,這種情況完全改變了。現在,只需要學習一種語言來寫前后端和命令行工具。Javascript 最初的設計是將其作為最終的膠水語言,試圖融合 HTML、CSS、面向對象編程、面向函數編程、動態語言、JITs 以及其它一切能通過 HTTP 請求得到的東西。

但是這樣不太好,因為后向兼容對于 web 的成功至關重要。要保證這一點,就無法修復一些嚴重錯誤。1995 年,經過 10 天的設計,Javascript 發布了。對于 10 天的成果而言,它相當優秀,但同時它也存在一些問題,無法對其進行修復。

這就是圖中唯一一個有雙向箭頭的地方:javascript 和 python 3 之間。我們把它叫做腳本語言的陰陽兩面。

大部分出現過的膠水 +web 語言正在消失,python 不在其列,至少目前還不會消失。我猜是因為 python 本身是合理的。使用 javascript 編程時間足夠長的話,過段段時間后就會變得不大正常。這時為了緩解壓力,程序員有可能會切換到 python。

同時,如果長時間使用 python,最后準備編寫 web 應用程序時,前端代碼和后端使用完全不同的語言是很煩人的。一個的語法是 [‘a’,‘b’,‘c’].join(’,’),而另一個則變成了’,’.join([‘a’,‘b’,‘c’]),這讓人完全記不清誰是誰了。

一種語言有 JIT,可以讓其一旦運行起來就會速度很快。而另一種則是啟動快,運行慢。

一種有合理的命名空間系統,而另一種則沒有。

我不清楚從長期看,python 3 是否能打敗 javascript。但至少目前看,它不會被擊敗。

同時,對于編程事實分支從不滿意的 Hejlsberg,看到了 javascript 的很多問題,引入了 TypeScript。與此同時,微軟突然停止了對 Windows 應用程序的大力推進,開始大面積推廣 web 和開源。這意味著 Microsoft 第一次將其開發者推向 web 語言即 javascript。在此基礎上,他們有自己的 TypeScript,我覺得這是一種很好的語言。這個分支存在有數十年,開始和其分支融合,可能不久后會消失。

TypeScript 和 javascript 比,能勝出嗎?這是個有趣的問題,我也不知道。我以前賭 Hejlsberg 能贏,不過我一般容易賭輸。

Python 2 和 Python 3 的對比

綜上所述,我對 python 2 和 3 有了結論。它們很相似,但不盡相同。我認為,這是因為他們在整個程序員語言遷移圖中所處的位置不同。Python 2 開發者來自 C 和 perl 開發人員,希望編寫膠水代碼。Web 服務器是后續添加的一個應用場景。我的意思是,python 2 出現后,web 程序變得流行起來,這并不出人意料。很多 python 2 的開發者轉到 Go 的開發,因為他們想寫的某些“系統膠水”代碼使用 Go 正合適。

Python 3 的開發者是從不同的語言切換而來的。事實證明,python 3 問世后,python 的使用得到很大的發展,不過新加入的人群和以前的人群有所不同。由于帶有模塊 SciPy 和 Tensorflow,從科學類和數值類處理轉過來的新程序員占了其中很大的比例。老實說,在高吞吐量的數值處理中,Python 是一個相當怪異的選擇。但不論如何,這些庫的存在是我們選擇它的一個原因。我猜 python 的另一個優勢則是易于和 C 模塊集成。當然,python 3 本身就是網絡編程。

想要理解 python 2 和 3 的區別,只需看看其不同的字符串類型。Python 2 中,字符串是一組字節,因為操作系統、Unix 管道處理、網絡 socket 的處理均以字節為單位。對于系統程序而言,python 2 是膠水語言,其處理以字節為單位。

在 python 3 中,字符串是一組 unicode 碼。因為人們不擅長 unicode 碼的轉換,而和網絡交互時,都是以 unicode 為基礎。做科學數值計算的人不關心字符串,做網絡編程的人更關心 unicode,所以 python 3 使用 unicode。如果要用 python 3 來編寫系統程序,就會一直疲于 unicode 的轉換,即使最簡單的文件名也需要進行轉換。這也正是有其因,必有其果。

【文章來源微信公眾號:每天學編程】---關注,后臺領取編程資源

?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 230,106評論 6 542
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 99,441評論 3 429
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 178,211評論 0 383
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 63,736評論 1 317
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 72,475評論 6 412
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 55,834評論 1 328
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,829評論 3 446
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 43,009評論 0 290
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 49,559評論 1 335
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 41,306評論 3 358
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 43,516評論 1 374
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 39,038評論 5 363
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 44,728評論 3 348
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 35,132評論 0 28
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 36,443評論 1 295
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 52,249評論 3 399
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 48,484評論 2 379

推薦閱讀更多精彩內容

  • TITLE: 編程語言亂燉 碼農最大的煩惱——編程語言太多。不是我不學習,這世界變化快! 有時候還是蠻懷念十幾、二...
    碼園老農閱讀 5,351評論 2 35
  • 計算機編程語言可用于將指令傳達給計算機。它們基于某些句法和語義規則,定義了編程語言中每種結構的含義。 現在我得到了...
    幻凌風閱讀 8,194評論 1 26
  • 還沒有從烏蘭巴托平淡的日子緩過勁來,在這個有些荒涼的舊首都的第一夜,便醉了。 抵達哈拉和林已經是晚上八九點鐘了,下...
    ll灼春ll閱讀 364評論 1 0
  • 08122-鐘明月 牙齒大街的新鮮事故事主要講述的是牙齒的牙洞里住著兩個可愛的東西,小朋友看著一排整齊的牙...
    797bb90c2602閱讀 491評論 0 0
  • 臨近春節到來的時候,天上終于開始朦朦飄起了雪。 那天晚上,我帶著妻子去見Simon。在我倆手挽著手路過一個個路燈時...
    浪堡堡閱讀 382評論 0 0