无法将(*struct)用作(*interface)的字段值。

huangapple go评论93阅读模式
英文:

Cannot use (*struct) as (*interface) in field value

问题

我有以下代码:

// eventloop.go
type Object interface {
    ActivateSlot(name string, parameters vector.Vector);
}



// main.go
import loop "./eventloop"

// ...

const slotname = "printer"

type printer struct {
    slot loop.Slot;
}

func (p *printer) Init() {
    p.slot = loop.Slot{slotname, p}; // offending line
}

func (p *printer) ActivateSlot(name string, parameters vector.Vector) {
    fmt.Println("Slot called: ", name); 
}

当我尝试编译时,我得到以下错误:

jurily@jurily ~/workspace/go $ ./build.sh
main.go:23: cannot use p (type *printer) as type *eventloop.Object in field value

如果我将有问题的行注释掉,它可以编译和运行正常。这里发生了什么?我漏掉了什么?

英文:

I have the following code:

// eventloop.go
type Object interface {
    ActivateSlot(name string, parameters vector.Vector);
}



// main.go
import loop "./eventloop"

// ...

const slotname = "printer"

type printer struct {
    slot loop.Slot;
}

func (p *printer) Init() {
    p.slot = loop.Slot{slotname, p}; // offending line
}

func (p *printer) ActivateSlot(name string, parameters vector.Vector) {
    fmt.Println("Slot called: ", name); 
}

When I try to compile, I get the following error:

jurily@jurily ~/workspace/go $ ./build.sh
main.go:23: cannot use p (type *printer) as type *eventloop.Object in field value

If I comment the offending line out, it compiles and runs fine. What's happening here? What am I missing?

答案1

得分: 4

更新:
这段代码在这里编译正常(都在同一个包中):

type Object interface {
    ActivateSlot(name string, parameters vector.Vector);
}
type Slot struct {
  name string;
  stuff Object;
}

const slotname = "printer"
type printer struct {
    slot Slot;
}
func (p *printer) Init() {
    p.slot = Slot{slotname, p}; // 有问题的那一行
}
func (p *printer) ActivateSlot(name string, parameters vector.Vector) {
    fmt.Println("调用了Slot:", name);
}

看起来你遗漏了一点,*printer 是 Object 类型,而你试图将它赋值给类型为 *Object 的字段,这是不同的类型。

在大多数情况下,你可以像上面那样编写代码 - 不使用指向接口类型的指针 - 但是如果你必须这样做,你可以这样编译:

type Slot struct {
  name string;
  stuff *Object;
}
func (p *printer) Init() {
     var o Object = p;
    p.slot = Slot{slotname, &o}; // 有问题的那一行
}

所以 p 是一个 Object,你需要取 p 的地址来匹配 *Object 的规范。

英文:

Update:
This code compiles fine here (all in the same package):

type Object interface {
    ActivateSlot(name string, parameters vector.Vector);
}
type Slot struct {
  name string;
  stuff Object;
}

const slotname = "printer"
type printer struct {
    slot Slot;
}
func (p *printer) Init() {
    p.slot = Slot{slotname, p}; // offending line
}
func (p *printer) ActivateSlot(name string, parameters vector.Vector) {
    fmt.Println("Slot called: ", name);
}

It seems that what you are missing is that *printer is of type Object, and you are trying to assign it to a field of type *Object, which is a different type.

In most cases you would write it like above - without pointers to interface types - but if you have to, you can make it compile like this:

type Slot struct {
  name string;
  stuff *Object;
}
func (p *printer) Init() {
     var o Object = p;
    p.slot = Slot{slotname, &o}; // offending line
}

So p is an Object, you need to take the address of p to match the *Object specification.

huangapple
  • 本文由 发表于 2009年11月30日 12:12:56
  • 转载请务必保留本文链接:https://go.coder-hub.com/1817809.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定