一、泛型的约束体系

Go 1.18引入的泛型通过接口作为约束(Constraint)来限定类型参数的能力范围。正确使用约束是写出高质量泛型代码的关键。

1.1 约束接口的演进

// Go 1.18前的约束方式(类型断言 + interface{}):
// func min(a, b interface{}) interface{} {
//     av := a.(int)  // 需要类型断言,容易panic
//     bv := b.(int)
//     if av < bv { return av }
//     return bv
// }

// Go 1.18+ 泛型约束:
// ① 基本约束(Comparable)
func contains[T comparable](slice []T, target T) bool {
    for _, v := range slice {
        if v == target { // comparable保证==/!=可用
            return true
        }
    }
    return false
}

// ② Ordered约束(支持比较运算符)
func min[T ordered](a, b T) T {
    if a < b { return a }
    return b
}

// ③ 自定义约束(interface + 类型列表)
type Integer interface {
    ~int | ~int8 | ~int16 | ~int32 | ~int64
    ~uint | ~uint8 | ~uint16 | ~uint32 | ~uint64
}

func sum[T Integer](values []T) T {
    var total T
    for _, v := range values {
        total += v
    }
    return total
}

// ~int 表示底层类型为int的所有类型(包括自定义别名)
type MyInt int
func test() {
    s := sum([]MyInt{1, 2, 3}) // MyInt底层是int,可参与sum
}

二、实用泛型设计模式

2.1 泛型Repository模式

// 传统写法:每个Entity重复相似的CRUD代码
type User struct { ID int64; Name string }
type Product struct { ID int64; Name string; Price float64 }

// 泛型版本:
type Entity interface {
    GetID() int64
}

type Repository[T Entity] struct {
    db  *sqlx.DB
    mu  sync.RWMutex
    mem map[int64]T
}

func NewRepository[T Entity](db *sqlx.DB) *Repository[T] {
    return &Repository[T]{
        db: db,
        mem: make(map[int64]T),
    }
}

func (r *Repository[T]) Create(ctx context.Context, entity T) error {
    r.mu.Lock()
    defer r.mu.Unlock()
    r.mem[entity.GetID()] = entity
    return nil
}

func (r *Repository[T]) GetByID(ctx context.Context, id int64) (T, error) {
    r.mu.RLock()
    defer r.mu.RUnlock()
    if entity, ok := r.mem[id]; ok {
        return entity, nil
    }
    var zero T
    return zero, ErrNotFound
}

// 使用:
type UserEntity struct { ID int64; Name string }
func (u UserEntity) GetID() int64 { return u.ID }

repo := NewRepository[UserEntity](db)
user, err := repo.GetByID(ctx, 1)

2.2 泛型Pipeline模式

// Pipeline:函数式数据处理
type Pipeline[T any] struct {
    data []T
}

func of[T any](items ...T) *Pipeline[T] {
    return &Pipeline[T]{data: items}
}

func (p *Pipeline[T]) Map[R any](fn func(T) R) *Pipeline[R] {
    result := make([]R, len(p.data))
    for i, v := range p.data {
        result[i] = fn(v)
    }
    return &Pipeline[R]{data: result}
}

func (p *Pipeline[T]) Filter(fn func(T) bool) *Pipeline[T] {
    result := make([]T, 0)
    for _, v := range p.data {
        if fn(v) {
            result = append(result, v)
        }
    }
    return &Pipeline[T]{data: result}
}

func (p *Pipeline[T]) Collect() []T {
    return p.data
}

// 使用示例(函数式链式调用):
numbers := of(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)

result := of(1, 2, 3, 4, 5, 6, 7, 8, 9, 10).
    Filter(func(n int) bool { return n%2 == 0 }).
    Map(func(n int) int { return n * n }).
    Map(func(n int) string { return fmt.Sprintf("val=%d", n) }).
    Collect()

// []string{"val=4", "val=16", "val=36", "val=64", "val=100"}

2.3 泛型错误处理模式

// Go泛型Result类型(类似Rust的Result)
type Result[T any] struct {
    value T
    err   error
}

func Ok[T any](value T) Result[T] {
    return Result[T]{value: value, err: nil}
}

func Err[T any](err error) Result[T] {
    return Result[T]{err: err}
}

func (r Result[T]) Unwrap() (T, error) {
    return r.value, r.err
}

func (r Result[T]) MustUnwrap() T {
    if r.err != nil {
        panic(r.err)
    }
    return r.value
}

// 使用:
func parseInt(s string) Result[int] {
    v, err := strconv.Atoi(s)
    if err != nil {
        return Err[int](err)
    }
    return Ok(v)
}

// 链式错误处理:
result := parseInt("42").
    Map(func(n int) int { return n * 2 }).
    Map(func(n int) int { return n + 1 })

value, err := result.Unwrap()
// value = 85, err = nil

三、泛型的性能与边界

// 泛型的编译时展开(Monomorphization)
// Go编译器为每个类型组合生成专用代码
// 泛型函数泛型本体 → 针对T=int生成分支 → 针对T=string生成分支

// benchmark对比:泛型 vs interface{}
func genericMin[T ordered](a, b T) T {
    if a < b { return a }
    return b
}

func interfaceMin(a, b interface{}) interface{} {
    av := a.(int)
    bv := b.(int)
    if av < bv { return av }
    return bv
}

// Benchmark结果:
// BenchmarkGeneric-8     1000000000   0.52 ns/op
// BenchmarkInterface-8   100000000    12.4 ns/op
// 泛型快24倍!(interface需要类型断言+装箱拆箱)

// ⚠️ 泛型的局限性:
// ① 不能约束方法的具体实现
type DataProcessor[T any] interface {
    Process(T) error  // 只能约束方法签名,不能提供默认实现
}

// ② 不能泛型方法(只能泛型函数或泛型类型)
// ❌ 不合法:
func (t T) process(item T) { } // 方法不能带类型参数

// ✅ 合法:类型本身泛型
type Processor[T any] struct {
    fn func(T) T
}
func (p Processor[T]) process(item T) T {
    return p.fn(item)
}