Golang泛型的高级用法

  1. 泛型函数的约束
// IsPositive 接口用于约束类型必须有 IsPositive 方法
type IsPositive interface {
    IsPositive() bool
}

// PrintIfPositive 是一个泛型函数,接受实现了 IsPositive 接口的参数
// 这样的约束提高了函数的通用性,但又确保传入的类型必须具备 IsPositive 方法。
// 下面的 PositiveInt 和 PositiveFloat 类型上,它们实现了 IsPositive 接口,从而可以被传递给 PrintIfPositive 函数
func PrintIfPositive[T IsPositive](value T) {
    if value.IsPositive() {
        fmt.Println(value)
    }
}

// 整数类型实现了 IsPositive 接口
type PositiveInt int

func (pi PositiveInt) IsPositive() bool {
    return pi > 0
}

// 浮点数类型实现了 IsPositive 接口
type PositiveFloat float64

func (pf PositiveFloat) IsPositive() bool {
    return pf > 0
}
  1. 泛型类型的约束
// Printer 接口用于约束类型必须有 Print 方法
// 约束确保传入的类型必须具备 Print 方法。
type Printer interface {
    Print()
}

// PrintPositive 是一个泛型函数,接受实现了 Printer 接口的参数
func PrintPositive[T Printer](value T) {
    value.Print()
}

// MyType 是一个自定义类型实现了 Printer 接口
// 从而可以被传递给 PrintPositive 函数。
type MyType int

func (mt MyType) Print() {
    fmt.Println(mt)
}
  1. 泛型函数与接口结合
// PrintElements 是一个泛型函数,接受实现了 Printer 接口的切片
// 这样的设计使得函数可以适用于多种不同类型的切片。
func PrintElements[T Printer](elements []T) {
    for _, element := range elements {
        element.Print()
    }
}

// IntPrinter 是一个整数类型实现了 Printer 接口
type IntPrinter int

func (ip IntPrinter) Print() {
    fmt.Println(ip)
}
  1. 泛型类型的递归
// TreeNode 是一个泛型二叉树节点。
// 它包含了左右子节点,这两个子节点也是 TreeNode 类型。这种设计在构建通用数据结构时非常有用。
type TreeNode[T any] struct {
    Value       T
    Left, Right *TreeNode[T]
}
  1. 泛型与反射
// GenericPrint 是一个泛型函数,使用反射打印值和类型
// 这使得函数能够处理各种类型的参数,但要注意反射可能带来一些性能开销。
func GenericPrint[T any](value T) {
    valueType := reflect.TypeOf(value)
    fmt.Printf("Type: %s, Value: %v\n", valueType, value)
}

单元测试代码如下:

func main() {
    // 运行单元测试
    fmt.Println("Running tests...")
    err := test()
    if err != nil {
        fmt.Println("Tests failed:", err)
    } else {
        fmt.Println("All tests passed.")
    }
}


// 单元测试

func test() error {
    // 1. 泛型函数的约束
    PrintIfPositive(PositiveInt(42))     // 输出:42
    PrintIfPositive(PositiveFloat(3.14)) // 输出:3.14
    PrintIfPositive(PositiveInt(-10))    // 未输出

    // 2. 泛型类型的约束
    PrintPositive(MyType(42)) // 输出:42

    // 3. 泛型函数与接口结合
    PrintElements([]IntPrinter{1, 2, 3, 4, 5}) // 输出:1 2 3 4 5

    // 4. 泛型类型的递归
    root := &TreeNode[int]{Value: 1}
    root.Left = &TreeNode[int]{Value: 2}
    root.Right = &TreeNode[int]{Value: 3}

    if root.Value != 1 || root.Left.Value != 2 || root.Right.Value != 3 {
        return fmt.Errorf("TreeNode test failed")
    }

    // 5. 泛型与反射
    GenericPrint(42)                 // 输出:Type: int, Value: 42
    GenericPrint("Hello, Generics!") // 输出:Type: string, Value: Hello, Generics!
    GenericPrint(3.14)               // 输出:Type: float64, Value: 3.14

    return nil
}

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注