Go 1.18 泛型如何使用接口定义新的类型参数

wen*_*ner 5 generics go

曾经在 go1.18beta1 中工作,但在 go1.18rc1 中不起作用

package main

type A struct{}

func (*A) Hello() {
    println("Hello")
}

func Create[M any, PT interface {
    Hello()
    *M
}](n int) (out []*M) {
    for i := 0; i < n; i++ {
        v := PT(new(M))
        v.Hello()
        out = append(out, v)
    }
    return
}

func main() {
    println(Create[A](2))
}
Run Code Online (Sandbox Code Playgroud)

执行会抛出

./prog.go:16:21: cannot use v (variable of type PT constrained by interface{Hello(); *M}) as type *M in argument to append:
    PT does not implement *M (type *M is pointer to interface, not interface)
Run Code Online (Sandbox Code Playgroud)

似乎是由于这个限制:

不允许将类型参数或指向类型参数的指针作为未命名字段嵌入到结构类型中。同样,不允许在接口类型中嵌入类型参数。目前还不清楚这些是否会被允许。

我怎样才能在 go1.18rc1 中做到这一点?

bla*_*een 4

你必须再次转换v回来*M

\n
out = append(out, (*M)(v))\n
Run Code Online (Sandbox Code Playgroud)\n

您得到的错误与可分配性有关。事实上,您问题中的引用并不禁止在接口中嵌入指针类型。和都是不同的命名类型参数,如果没有显式转换MPT则无法将其中一个指定给另一个。

\n

相反,转换是有效的,因为PT\xe2\x80\x99s 类型集中的所有类型(仅*M)都可以转换为*M

\n