ZingLix Blog

这里是 ZingLix 的个人博客,与你一起在计算机的世界探索~

马上订阅 ZingLix Blog RSS 更新: https://zinglix.xyz/feed.xml

Go 在使用泛型时无法与 Pointer Receiver 共存的解决方法

2024年1月24日 08:00
Go

问题描述

在使用 Go 的泛型时,如果泛型类型存在 constraint,而传入的类型在实现这个 constraint 时使用的是 pointer receiver,那么就会遇到 XXX does not satisfy XXX (method XXX has pointer receiver) 的报错,就比如下面这个例子希望用 Create 函数完成所有创建 Person 的操作

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
type Person interface {
	SetID(id int)
}

type Student struct {
	ID int
}

func (p *Student) SetID(id int) {
	p.ID = id
}

func Create[T Person](id int) *T {
	var person T
	person.SetID(id)
	return &person
}

这里 Student(p *Student) 实现了 Person,然而如果用 Create[Student](id) 这种方式调用时,编译会遇到这个报错

1
Student does not satisfy Person (method SetID has pointer receiver)

问题解释

问题就在于这段代码中的 (p *Student)

1
2
3
func (p *Student) SetID(id int) {
	p.ID = id
}

在 Go 中会认为是 *Student 实现了 SetID 方法,或者说实现了 Person interface,而不是 Student,因此提示 Student 并不满足 Person

那一个办法是把实现 interface 传入的改成 value receiver

1
2
3
func (p Student) SetID(id int) {  // 传入的 p 类型去掉了 *
	p.ID = id
}

这样可以通过编译且正常运行,但问题是变成了值传递后,SetID 并不会作用于传入的那个变量,这个函数也形同虚设。

另一个解决方案是可以把调用函数时改成 Create[*Student](1),加上这个 *,报错也会随之消除。但问题就解决了吗?...

剩余内容已隐藏

查看完整文章以阅读更多