Go1.24 新特性:泛型再查缺補(bǔ)漏,正式支持類型別名!
大家好,我是煎魚。
自從 Go1.18 支持泛型后,社區(qū)很多同學(xué)以為泛型會帶來非常巨大的改變。但實際上,還是比較尷尬的。因為泛型還在持續(xù)的迭代中,還處于發(fā)展期。
今天給大家分享的是 Go1.24 中給泛型加的新功能特性。一起來學(xué)習(xí)吧!
背景
泛型提案說:"類型別名(type alias)可以引用泛型,但類型別名不能有自己的參數(shù)。之所以有這一限制,是因為不清楚如何處理具有約束的類型參數(shù)的類型別名"。
對應(yīng)的場景例子,一般聲明是如下代碼:
type A = P
但是在 Go1.24 以前,A 沒法包含泛型的類型參數(shù)。Go 官方在 go ref/spec#Alias_declarations[1] 中明確提到這種聲明方式是會報錯的:
type A[P any] = P // illegal: P is a type parameter
本次新的提案《spec: generics: permit type parameters on aliases[2]》專門針對這個問題給出了新的處理思路。
提案作者 @Matthew Dempsky 建議放寬這一限制,允許類型別名擁有自己的類型參數(shù)。
他認(rèn)為有一種明確的方法可以處理帶有約束類型參數(shù)的類型別名:“類型別名的使用需要滿足約束,而在底層類型表達(dá)式中,這些參數(shù)可以用來實例化它們所滿足的其他泛型。”
Go1.24:泛型支持類型別名
終于,經(jīng)過一番 issues 討論和整合(花了 4 年?。。。┰诩磳?2 月份發(fā)布 Go1.24 將會支持類型別名。
具體的 Go1.24 的使用例子如下:
// 定義一個通用切片類型
type GenericSlice[T any] = []T
// 示例:自定義結(jié)構(gòu)體切片
type Fish struct {
Name string
IsGrilled bool
Ingredients []string
}
func main() {
// 示例:字符串切片
words := GenericSlice[string]{"Go", "Rocks"}
fmt.Println("Words:", words)
fishes := GenericSlice[Fish]{
{Name: "Salmon", IsGrilled: true, Ingredients: []string{"Salt", "Lemon", "Garlic"}},
{Name: "Tuna", IsGrilled: false, Ingredients: []string{"Soy Sauce", "Wasabi"}},
}
fmt.Println("Grilled Fish Menu:", fishes)
}
輸出結(jié)果:
Words: [Go Rocks]
Grilled Fish Menu: [{Salmon true [Salt Lemon Garlic]} {Tuna false [Soy Sauce Wasabi]}]
如果你是 Go1.23 的版本,將會報:./prog.go:6:6: generic type alias requires GOEXPERIMENT=aliastypeparams 這個錯誤。
是因為該特性在 Go1.23 起作為實驗特性加入。在 Go1.24 計劃正式轉(zhuǎn)正。
總結(jié)
自 Go1.18 泛型正式加入 Go 這門編程語言來,感覺一直還在修修補(bǔ)補(bǔ)的路上。這次支持類型別名,也花了將近 4 年。
雖然整體還能用,但是還是磕磕碰碰。希望越來越好了。
參考資料
[1]go ref/spec#Alias_declarations: https://tip.golang.org/ref/spec#Alias_declarations
[2]spec: generics: permit type parameters on aliases: https://github.com/golang/go/issues/46477