gpt4 book ai didi

pointers - Go 使用指针接收者调用函数的语法

转载 作者:IT王子 更新时间:2023-10-29 00:48:37 27 4
gpt4 key购买 nike

在 Go 中,如果我定义一个带有指针的函数作为接收者,难道它不应该只允许从指针调用该函数吗?为什么从值本身调用这个函数就可以了,效果是一样的。

例如,在下面的程序中:m1.reset() 和 m2.reset() 具有相同的效果。尽管 m1 是一个值而 m2 是一个指针。

我有点困惑,因为有两种方法可以做同样的事情,我不确定应该遵循哪一种。虽然大部分代码都遵循使用指针字段调用函数的约定。我错过了什么吗?

package main

import "fmt"

type MyStruct struct {
X int
}

func (m *MyStruct) reset() {
m.X = 0
}

func main() {
m1 := MyStruct{1}
m2 := &MyStruct{1}

fmt.Println(m1.X)
fmt.Println(m2.X)

m1.reset()
m2.reset()

fmt.Println(m1.X)
fmt.Println(m2.X)
}

最佳答案

@jnml 提供了完美的文档规范解释,但我想添加一个基于您的代码示例。我认为您的重点不应该是“为什么有两种方法可以做同样的事情”,而应该更多地关注何时使用一种与另一种。以指针作为接收者的方法能够修改该接收者的值,而以值作为接收者的方法则不能。这是因为这些方法接收到接收器的副本。当你得到一个指针的副本时,你仍然可以修改它的值。当您收到值的副本时,您在该方法中所做的更改只会更改副本,而不会更改原始值:

package main

import "fmt"

type MyStruct struct {
X int
}

func (m *MyStruct) resetPtr() {
m.X = 0
}

func (m MyStruct) resetValue() {
m.X = 0
}

func main() {
m1 := MyStruct{1}
m2 := &MyStruct{1}

fmt.Println("Original Values:", m1.X, m2.X)

m1.resetPtr()
m2.resetPtr()

fmt.Println("After resetPtr():", m1.X, m2.X)

m1 = MyStruct{1}
m2 = &MyStruct{1}

m1.resetValue()
m2.resetValue()

fmt.Println("After resetValue():", m1.X, m2.X)
}

输出

Original Values: 1 1
After resetPtr(): 0 0
After resetValue(): 1 1

您可以看到访问这些变量的方式并不是真正的问题所在。更多的是关于您可以在方法内部使用它们做什么,以及如何将它们作为参数传递给其他函数或方法(被复制)。

关于pointers - Go 使用指针接收者调用函数的语法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9958064/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com