首頁 > 軟體

Go1.20 arena新特性範例詳解

2022-11-17 14:00:32

正文

大概半年前,我寫過一篇文章《Go 要違背初心嗎?新提案:手動管理記憶體》。有興趣了深入解的同學,可以再回顧一下。

當時我們還想著 Go 團隊應該不會接納,至少不會那麼快:

懶得翻也可以看我再次道來,本文提到的提案《proposal: arena: new package providing memory arenas》,這其中的 Arena 將會是一個突破項。

快速背景

Arena 指的是一種從一個連續的記憶體區域分配一組記憶體物件的方式。優點比一般的記憶體分配更有效率,也可以一次性釋放。當然了,它的重點是要手動管理記憶體

Go 團隊希望加進 Go 特性中,範例程式碼如下:

import (
 「arena」
 …
)
type T struct {
 val int
}
func main() {
 a := arena.New()
 var ptrT *T
 a.New(&ptrT)
 ptrT.val = 1
 var sliceT []T
 a.NewSlice(&sliceT, 100)
 sliceT[99].val = 4
 a.Free()
}

手動呼叫 arena.New 方法分配 arena 記憶體,再呼叫 Free 方法進行釋放。

簡單來講就是可以手動管理記憶體,就可以做很多事了,也 “容易” 崩。

最新進展

這個提案一直在 issues 上適度的爭議討論,@Michael Knyszek 大佬程式碼寫的很快,已經直接提交上去了...直到最近被人發現,讓他更新進度。

已經明確:Go1.20 將會支援 arena 特性,通過 GOEXPERIMENT=arena 來開啟,接受大家的 review 和使用,抗阻很小。

已實現 API 和原提案不同的地方有:

  • API 使用了泛型,例如:arena.New[int](myArena "int")
  • Arena 的 塊大小是 8 MiB 而不是 64 MiB,似乎在更多情況下提供了更好的效能。
  • MSAN 和 ASAN 模式可用於識別不會導致崩潰的 use-after-free 錯誤(記憶體損壞應該仍然是不可能的)。 需注意,這些模式對非 cgo 的 Go 程式幾乎沒有作用。Arena 是個例外。

另外根據社群的反饋,可能還會出現配套型別的 Arena。如下函數簽名:

// MakeMap creates a new map[K]V with the provided capacity.
// The map[K]V must not be used after the arena is freed.
// Accessing the underlying storage of the map after free may result in a fault,
// but this fault is also not guaranteed.
func MakeMap[K comparable, V any](a *Arena, cap int "K comparable, V any") map[K]V { ... }

在 Go1.20 釋出該新特性的話,按照發布週期計劃,是 2 月份左右釋出,相信大家很快就能用上,可以多多關注。

總結

一開始瞭解這個提案時,還想著 Go 搞了快 10 年才採納和推進泛型。這 Arena 應該不至於這麼快吧?畢竟加進去了,許多程式都可以寫的複雜起來。

沒想到...現實打臉來的太快,推進的很快。

就像其他小夥伴說的,這可以從程式碼優化效能,而不需要砍需求。也是一個有意思且不錯的源動力!

據小道訊息,某些同學表示在框架和其它場景測過,有說變得快了,有說沒差多少。比較迷,提案內暫時未提供測試報告,不好定論。

Go 1.20 Beta 將在未來幾周內(2022.11 月底前)釋出,讓我們拭目以待:)

以上就是Go1.20 arena新特性範例詳解的詳細內容,更多關於Go1.20 arena新特性的資料請關注it145.com其它相關文章!


IT145.com E-mail:sddin#qq.com