Golang泛型的使用方法詳解
1. 泛型是什么
泛型生命周期只在編譯期,旨在為程序員生成代碼,減少重復(fù)代碼的編寫
在比較兩個數(shù)的大小時,沒有泛型的時候,僅僅只是傳入類型不一樣,我們就要再寫一份一模一樣的函數(shù),如果有了泛型就可以減少這類代碼
// int
func GetMaxNumInt(a, b int) int {
if a > b {
return a
}
return b
}
// int8
func GetMaxNumInt8(a, b int8) int8 {
if a > b {
return a
}
return b
}
2. 泛型的簡單使用
2.1. 泛型示例
需要go版本大于等于1.18
我們先改造一下上面的示例,只需要在函數(shù)后用中括號聲明T可能出現(xiàn)的類型,中間用符號"|" 分隔
// 使用泛型
func GetMaxNum[T int | int8](a, b T) T {
if a > b {
return a
}
return b
}
2.2. 自定義泛型類型
如果類型太多了怎么辦呢?這時候我們就可以自定義泛型類型
// 像聲明接口一樣聲明
type MyInt interface {
int | int8 | int16 | int32 | int64
}
// T的類型為聲明的MyInt
func GetMaxNum[T MyInt](a, b T) T {
if a > b {
return a
}
return b
}
2.3. 調(diào)用帶泛型的函數(shù)
如何調(diào)用這個帶有泛型的函數(shù)呢?
var a int = 10 var b int = 20 // 方法1,正常調(diào)用,編譯器會自動推斷出傳入類型是int GetMaxNum(a, b) // 方法2,顯式告訴函數(shù)傳入的類型是int GetMaxNum[int](a, b)
3. 自定義泛型類型的語法
在2.2小節(jié)中我們可以看到一個泛型的簡單自定義類型,本節(jié)將會詳細(xì)描述泛型自定義類型的語法
3.1. 內(nèi)置的泛型類型any和comparable
any: 表示go里面所有的內(nèi)置基本類型,等價于interface{}

comparable: 表示go里面所有內(nèi)置的可比較類型:int、uint、float、bool、struct、指針等一切可以比較的類型

3.2. 聲明一個自定義類型
跟聲明接口一樣,使用type x interface{} 關(guān)鍵字來聲明,不過里面的成員不再是方法,而是類型,類型之間用符號 "|" 隔開
type MyInt interface {
int | int8 | int16 | int32 | int64
}
成員類型支持go中所有的基本類型
type MyT interface {
int | float32 | bool | chan int | map[int]int | [10]int | []int | struct{} | *http.Client
}
3.3. 泛型中的"~"符號是什么
符號"~"都是與類型一起出現(xiàn)的,用來表示支持該類型的衍生類型
// int8的衍生類型
type int8A int8
type int8B = int8
// 不僅支持int8, 還支持int8的衍生類型int8A和int8B
type MyInt interface {
~int8
}
4. 泛型的進(jìn)階使用
4.1. 泛型與結(jié)構(gòu)體
創(chuàng)建一個帶有泛型的結(jié)構(gòu)體User,提供兩個獲取age和name的方法
注意:只有在結(jié)構(gòu)體上聲明了泛型,結(jié)構(gòu)體方法中才可以使用泛型
type AgeT interface {
int8 | int16
}
type NameE interface {
string
}
type User[T AgeT, E NameE] struct {
age T
name E
}
// 獲取age
func (u *User[T, E]) GetAge() T {
return u.age
}
// 獲取name
func (u *User[T, E]) GetName() E {
return u.name
}
我們可以通過聲明結(jié)構(gòu)體對象時,聲明泛型的類型來使用帶有泛型的結(jié)構(gòu)體
// 聲明要使用的泛型的類型 var u User[int8, string] // 賦值 u.age = 18 u.name = "weiwei" // 調(diào)用方法 age := u.GetAge() name := u.GetName() // 輸出結(jié)果 18 weiwei fmt.Println(age, name)
5. 泛型的限制或缺陷
5.1 無法直接和switch配合使用
將泛型和switch配合使用時,無法通過編譯
func Get[T any]() T {
var t T
switch T {
case int:
t = 18
}
return t
}
只能先將泛型賦值給interface才可以和switch配合使用
func Get[T any]() T {
var t T
var ti interface{} = &t
switch v := ti.(type) {
case *int:
*v = 18
}
return t
}
到此這篇關(guān)于Golang泛型的使用方法詳解的文章就介紹到這了,更多相關(guān)Golang泛型內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
多階段構(gòu)建優(yōu)化Go?程序Docker鏡像
這篇文章主要為大家介紹了多階段構(gòu)建優(yōu)化Go?程序Docker鏡像,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-08-08
go語言開發(fā)環(huán)境配置(sublime text3+gosublime)
網(wǎng)上google了下go的開發(fā)工具,大都推薦sublime text3+gosublime,本文就介紹了go語言開發(fā)環(huán)境配置(sublime text3+gosublime),具有一定的參考價值,感興趣的可以了解一下2022-01-01
golang 實(shí)現(xiàn)時間滑動窗口的示例代碼
滑動時間窗口就是把一段時間片分為多個樣本窗口,可以通過更細(xì)粒度對數(shù)據(jù)進(jìn)行統(tǒng)計(jì),這篇文章主要介紹了golang 實(shí)現(xiàn)時間滑動窗口,需要的朋友可以參考下2022-10-10
Golang中的自定義類型之間的轉(zhuǎn)換的實(shí)現(xiàn)(type conversion)
這篇文章主要介紹了Golang中的自定義類型之間的轉(zhuǎn)換的實(shí)現(xiàn)(type conversion),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2021-02-02
GoLang語法之標(biāo)準(zhǔn)庫fmt.Printf的使用
fmt包實(shí)現(xiàn)了類似C語言printf和scanf的格式化I/O,主要分為向外輸出內(nèi)容和獲取輸入內(nèi)容兩大部分,本文就來介紹一下GoLang語法之標(biāo)準(zhǔn)庫fmt.Printf的使用,感興趣的可以了解下2023-10-10

