Golang面試:泛型

落雷發表於2024-07-03

Go語言在1.18版本中引入了泛型(Generics),這是Go語言發展中的一個重要里程碑。泛型允許你編寫更通用和可複用的程式碼,而無需犧牲型別安全性。以下是對Go中泛型的詳細介紹,包括其語法、使用場景和示例程式碼。

1. 泛型的基本概念

泛型允許你定義可以處理多種資料型別的函式和資料結構,而無需為每種型別編寫單獨的程式碼。透過使用型別引數,你可以編寫一次程式碼,然後在不同的上下文中重用它。

2. 型別引數

型別引數是泛型的核心。你可以在函式、結構體和介面中使用型別引數。型別引數在宣告時使用方括號[]括起來,並且可以有一個或多個型別引數。

3. 型別約束

型別約束用於限制型別引數可以接受的型別。Go提供了幾種型別約束:

  • any:表示任意型別。
  • comparable:表示可以進行比較的型別(支援==!=操作)。
  • 可以定義自定義型別約束:
package main

import "fmt"

// 定義一個自定義型別約束
type Number interface {
	int | float64
}

// 使用自定義型別約束的泛型函式
func Add[T Number](a, b T) T {
	return a + b
}

func main() {
	fmt.Println(Add(1, 2))       // 輸出: 3
	fmt.Println(Add(1.5, 2.3))   // 輸出: 3.8
}

在這個示例中,Number介面定義了一個自定義型別約束,表示intfloat64型別。

4. 泛型的使用場景

泛型在以下場景中特別有用:

  • 集合操作:例如,處理不同型別的列表、集合和對映。
  • 演算法實現:例如,排序、搜尋和數學運算。
  • 資料結構:例如,棧、佇列和樹。
  • 通用庫:例如,通用的工具函式和資料處理庫。

5. 注意事項

  • 效能:泛型可能會引入一些效能開銷,特別是在編譯時和執行時的型別檢查和轉換。
  • 複雜性:泛型程式碼可能會增加程式碼的複雜性,特別是在型別約束和型別引數的使用上。

6. 示例

建立一個泛型函式,該函式可以接受任何型別的map並返回其鍵的列表。為了實現這一點,我們需要定義一個泛型型別引數來表示map的鍵和值的型別。

package main

import (
	"fmt"
)

// GetKeys 返回給定 map 的所有鍵的切片
func GetKeys[K comparable, V any](m map[K]V) []K {
	keys := make([]K, 0, len(m))
	for k := range m {
		keys = append(keys, k)
	}
	return keys
}

func main() {
	// 示例 1:map[string]int
	map1 := map[string]int{
		"one": 1,
		"two": 2,
		"three": 3,
	}
	keys1 := GetKeys(map1)
	fmt.Println("Keys of map1:", keys1)

	// 示例 2:map[int]string
	map2 := map[int]string{
		1: "one",
		2: "two",
		3: "three",
	}
	keys2 := GetKeys(map2)
	fmt.Println("Keys of map2:", keys2)

	// 示例 3:map[float64]bool
	map3 := map[float64]bool{
		1.1: true,
		2.2: false,
		3.3: true,
	}
	keys3 := GetKeys(map3)
	fmt.Println("Keys of map3:", keys3)
}

說明

  1. 定義泛型函式
    • 函式GetKeys使用兩個型別引數KV,其中K表示map的鍵型別,V表示map的值型別。
    • K需要實現comparable介面,因為map的鍵必須是可比較的。
    • V可以是任何型別,因此使用any作為型別約束。
  2. 獲取鍵列表
    • 函式中,建立一個切片keys用於儲存map的鍵。
    • 透過遍歷map,將每個鍵新增到keys切片中。
    • 最後返回keys切片。
  3. 示例用法
    • main函式中,定義了三個不同型別的map,並呼叫GetKeys函式獲取它們的鍵列表。
    • 列印每個map的鍵列表以驗證結果。

孟斯特

宣告:本作品採用署名-非商業性使用-相同方式共享 4.0 國際 (CC BY-NC-SA 4.0)進行許可,使用時請註明出處。
Author: mengbin
blog: mengbin
Github: mengbin92
cnblogs: 戀水無意
騰訊雲開發者社群:孟斯特


相關文章