小编典典

指针接收器和值接收器在Golang中是什么意思?

go

我一直在从关于指针接收器的话题中出错,我决定用谷歌搜索术语的含义,并且阅读了有关指针接收器的不同资源和文档。例如:http
:
//golang.org/doc/faq和http://jordanorelli.com/post/32665860244/how-
to-use-interfaces-in-go。

虽然,尽管他们谈论这些术语,但仍未能准确定义它们。不过,从上下文来看,我认为它们之间的区别在于将变量定义为类似*MyStructvs的指针MyStruct。尽管我不是100%肯定它们之间的区别,但我想对这些术语,尤其是它们的区别(指针接收者和值接收者)有一个更正式或扎实的理解。如果可能的话,一些简单的示例代码将显示它们在运行中的不同之处,那就太棒了!(可能是真正理解这一点所必需的)

例如,令我感到困惑的是,术语“指针”和“指针接收器”之间有什么区别?还是价值和价值接收者?接收者一词对这些概念有什么补充?


阅读 292

收藏
2020-07-02

共1个答案

小编典典

既然您已经弄清楚了,您对术语“ 接收者”
而不是指针/值的区别感到困惑。在Go中,“接收器”是指为接口目的而在方法上定义的值。您可以将接收器视为函数的第一个参数的特例。

func (m MyStruct) DoStuff()

这就是所谓的“值接收器”,它在 MyStruct 上定义。这在功能上等同于:

func DoStuff(m MyStruct)

除:

使用“接收器”,您可以使用“。”来调用函数,就像在许多OO语言中一样:

 m := MyStruct{} 
 m.DoStuff() // as opposed to DoStuff(m)

类型是接收者的一组方法定义了它实现的接口:

type DoesStuff interface {
    DoStuff()
}

func DoSomething(d DoesStuff) {
    d.DoStuff()
}

func main() {
    m := MyStruct{}
    DoSomething(m)
}

那么什么是指针接收器?看起来像这样:

func (m *MyStruct) DoOtherStuff()

区别恰恰是指针和值之间的区别。尽管会发生轻微的语义变化。Go会自动寻址和自动取消引用指针(在大多数情况下),因此m := MyStruct{}; m.DoOtherStuff()Go仍然可以工作,因为Go会自动(&m).DoOtherStuff()为您服务。(自然,您也可以自由地做m := &MyStruct{}; m.DoOtherStuff)。此外,接口是在指针上定义的,因此:

type DoesOtherStuff interface {
    DoOtherStuff()
}

func DoSomethingElse(d DoesOtherStuff) {
    d.DoOtherStuff()
}

func main() {
    m := MyStruct{}
    // DoSomethingElse(m) will fail since because the interface
    // DoesOtherStuff is defined on a pointer receiver and this is a value
    DoSomethingElse(&m)
}

如果您仍然对 何时
使用指针接收器与变量接收器感到困惑,那么简短的答案是:可能是指针接收器。长答案已经被回答了好几次,但是我将其链接到这里仅仅是因为在我的历史记录中很容易找到它。

2020-07-02