Go 错误:“嵌入类型不能是指向接口的指针”

Sot*_*liu 2 struct pointers interface build go

以下代码给出编译时错误:

type IFile interface {
    Read() (n int, err error)
    Write() (n int, err error)
}

type TestFile struct {
   *IFile
}
Run Code Online (Sandbox Code Playgroud)

错误:

./test.go:18:嵌入类型不能是指向接口的指针

为什么我不能嵌入*IFile

icz*_*cza 5

语言规范不允许这样做。规范中的相关部分:结构类型:

使用类型声明但没有显式字段名称的字段是匿名字段,也称为嵌入字段或结构中类型的嵌入。嵌入类型必须指定为类型名称T或指向非接口类型名称的指针*T,并且T其本身可能不是指针类型。非限定类型名称充当字段名称。

指向接口类型的指针很少有用,因为接口类型可能保存指针或非指针值。

话虽如此,如果实现您的IFile类型的具体类型是指针类型,那么指针值将被包装在 type 的接口值中IFile,因此您仍然需要 embed IFile,只是实现的值IFile将是指针值,例如

// Let's say *FileImpl implements IFile:
f := TestFile{IFile: &FileImpl{}}
Run Code Online (Sandbox Code Playgroud)

编辑:回答您的评论:

首先,这是 Go,而不是 C++。在 Go 中,接口不是指针,但它们表示为一对(type;value),其中“值”可以是指针或非指针。有关此内容的更多信息,请参阅博客文章:反射定律:接口的表示

其次,如果FileImpl是一种类型,f := TestFile{IFile : &FileIml}显然是一个编译时错误,您需要一个值*FileImpl,但&FileImpl显然不是。例如,您需要一个复合文字,其形式为&FileImpl{},所以它应该像我上面发布的那样。