Go 部落格

Go 2,我們來了!

Robert Griesemer
2018 年 11 月 29 日

背景

在 GopherCon 2017 大會上,Russ Cox 透過他的演講Go 的未來 (部落格文章) 正式啟動了關於下一個 Go 大版本的思考過程。我們非正式地將這個未來的語言版本稱為 Go 2,儘管我們現在明白它將透過增量步驟而非一次大爆炸式的單一主要釋出版本到來。然而,Go 2 仍然是一個有用的稱謂,至少為討論那個未來的語言版本提供了一種方式,所以我們暫時繼續使用它。

Go 1 和 Go 2 之間的一個主要區別在於誰將影響設計以及如何做出決策。Go 1 是一個小團隊的努力成果,受外部影響不大;Go 2 將更多地由社群驅動。經過近 10 年的使用,我們對這門語言和庫有了很多最初不知道的認識,這隻有透過 Go 社群的反饋才得以實現。

2015 年,我們引入了提案流程來收集特定型別的反饋:關於語言和庫變更的提案。由資深 Go 團隊成員組成的委員會一直在定期審查、分類和決定收到的提案。這項工作進展順利,但作為流程的一部分,我們忽略了所有不向後相容的提案,而是簡單地將它們標記為 Go 2。2017 年,我們還停止進行任何型別的增量向後相容的語言更改,無論多小,轉而支援一個更全面的計劃,該計劃考慮了 Go 2 的更廣闊前景。

現在是時候對 Go 2 提案採取行動了,但在此之前,我們需要一個計劃。

狀態

撰寫本文時,大約有 120 個標記為 Go 2 proposal 的未解決問題。每個問題都提出了重大的庫或語言變更,這些變更通常不滿足現有的Go 1 相容性保證。Ian Lance Taylor 和我一直在處理這些提案,並對其進行了分類(Go2CleanupNeedsDecision 等),以瞭解情況並方便後續處理。我們還合併了相關的提案,並關閉了那些看起來明顯超出 Go 範圍或無法採取行動的提案。

剩餘提案中的想法可能會影響 Go 2 的庫和語言。早期出現了兩個主要主題:支援更好的錯誤處理和泛型。今年 GopherCon 上已經發布了這兩個領域的設計草案,還需要進行更多探索。

那剩下的呢?我們受到這樣一個事實的約束:現在有數百萬 Go 程式設計師和大量的 Go 程式碼,我們需要將它們全部帶入 Go 2,以免導致生態系統分裂。這意味著我們不能進行很多更改,並且我們將要進行的更改需要仔細選擇。為了取得進展,我們正在為這些重大的潛在更改實施新的提案評估流程。

提案評估流程

提案評估流程的目的是收集對少量選定提案的反饋,以便做出最終決定。該流程或多或少與釋出週期並行執行,包含以下步驟

  1. 提案選擇。Go 團隊選擇少量Go 2 提案,這些提案看起來值得考慮接受,但尚未做出最終決定。有關選擇標準的更多資訊,請參見下文。

  2. 提案反饋。Go 團隊釋出公告,列出選定的提案。公告向社群解釋了推進選定提案並收集每個提案反饋的初步意圖。這讓社群有機會提出建議和表達擔憂。

  3. 實現。根據反饋,實施提案。這些重要的語言和庫變更的目標是在即將到來的釋出週期第一天準備好提交。

  4. 實現反饋。在開發週期中,Go 團隊和社群有機會實驗新功能並收集進一步的反饋。

  5. 釋出決定。在三個月開發週期結束時( just在釋出前開始為期三個月的倉庫凍結時),Go 團隊根據釋出週期期間收集的經驗和反饋,最終決定是否釋出每個更改。這提供了一個機會來考慮更改是否帶來了預期的好處或產生了任何意外的成本。一旦釋出,更改將成為語言和庫的一部分。被排除的提案可能會重新評估或永久拒絕。

透過兩輪反饋,這個流程傾向於拒絕提案,這有望防止特性蔓延並有助於保持語言的小巧和簡潔。

我們無法對每個未解決的 Go 2 提案都走一遍這個流程,數量實在太多了。這就是選擇標準發揮作用的地方。

提案選擇標準

一項提案至少必須

  1. 解決許多人的重要問題,

  2. 對其他所有人的影響最小,並且

  3. 有一個清晰且易於理解的解決方案.

要求 1 確保我們進行的任何更改都能儘可能多地幫助 Go 開發者(使他們的程式碼更健壯、更容易編寫、更可能正確等等),而要求 2 則確保我們謹慎地儘量少地傷害開發者,無論是破壞他們的程式還是導致其他變動。根據經驗法則,我們應該爭取透過一項給定的更改幫助的開發者數量至少是我們傷害的開發者數量的十倍。不影響實際 Go 使用的更改,其好處相對於巨大的實現成本而言為零,應該避免。

沒有要求 3,我們就無法實現該提案。例如,我們相信某種形式的泛型可能為很多人解決一個重要問題,但我們還沒有一個清晰且易於理解的解決方案。這沒關係,這隻意味著在考慮該提案之前,需要重新評估。

提案

我們認為這是一個很好的計劃,應該對我們很有幫助,但重要的是要明白這只是一個起點。隨著流程的使用,我們會發現它運作不暢的地方,並根據需要對其進行改進。關鍵在於,除非我們在實踐中使用它,否則我們不會知道如何改進它。

一個安全的起點是少量的向後相容的語言提案。我們已經很長時間沒有進行語言更改了,所以這讓我們回到了那種模式。此外,這些更改不會要求我們擔心破壞現有程式碼,因此它們可以作為完美的試驗氣球。

說了這麼多,我們為 Go 1.13 版本提出了以下 Go 2 提案的選擇(提案評估流程的步驟 1)

  1. #20706 基於 Unicode TR31 的通用 Unicode 識別符號:這解決了使用非西方字母表的 Go 程式設計師的一個重要問題,並且對其他任何人幾乎沒有影響。有一些規範化問題需要我們回答,並且社群反饋將很重要,但之後實現路徑是明確的。請注意,識別符號匯出規則不會受此影響。

  2. #19308, #28493 二進位制整數文字和數字文字中對 _ 的支援:這些是相對較小的更改,但在許多程式設計師中似乎非常受歡迎。它們可能沒有完全達到解決“重要問題”的門檻(十六進位制數字目前為止執行良好),但它們在這方面使 Go 與大多數其他語言持平,並緩解了部分程式設計師的痛點。它們對不關心二進位制整數文字或數字格式的其他人的影響最小,並且實現是明確的。

  3. #19113 允許帶符號整數作為移位計數:據估計,所有非常量移位中約有 38% 需要(人工)uint 轉換(詳見該問題)。這項提案將清理大量程式碼,使移位表示式與索引表示式以及內建函式 cap 和 len 更好地同步。它將主要對程式碼產生積極影響。實現是明確的。

下一步

透過這篇部落格文章,我們已經執行了提案評估流程的第一步,並開始了第二步。現在輪到你們,Go 社群,就上面列出的問題提供反饋了。

對於每個我們收到清晰且贊同反饋的提案,我們將繼續進行實現(流程的步驟 3)。因為我們希望在下一個釋出週期的第一天(暫定 2019 年 2 月 1 日)實現這些更改,所以這次我們可能會稍微提前開始實現,以便留出整整兩個月的反饋時間(2018 年 12 月,2019 年 1 月)。

在 3 個月的開發週期(2019 年 2 月至 5 月)內,選定的功能將被實現並在 tip 上可用,所有人都有機會體驗它們。這提供了另一個反饋機會(流程的步驟 4)。

最後,在倉庫凍結(2019 年 5 月 1 日)後不久,Go 團隊會做出最終決定,是永久保留新功能(並將其包含在 Go 1 相容性保證中),還是放棄它們(流程的最後一步)。

(由於在倉庫凍結時可能需要移除某個功能,因此實現方式需要使得該功能可以在不破壞系統其他部分穩定性的情況下停用。對於語言更改,這可能意味著所有與功能相關的程式碼都由內部標誌保護。)

這將是我們第一次遵循這個流程,因此倉庫凍結也將是一個回顧流程並在必要時進行調整的好時機。讓我們看看效果如何。

祝評估愉快!

下一篇文章:2019 年的 Go Modules
上一篇文章:Go 的九年
部落格索引