如何确定作为函数参数传递的指针是被修改还是被复制修改的?

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

How to determine if the pointer passed as a function argument is being modified or a copy is being modified?

问题

package main

import (
	"fmt"
)

type Numbers struct {
	x int
	y int
}

func initial(number *Numbers) {
	number.x = 1
	number.y = 1
}

func final(number *Numbers) {
	number = &Numbers{2, 2}
}

func main() {
	p := Numbers{0, 0}
	fmt.Println(p) //输出 {0 0}

	initial(&p)
	fmt.Println(p) //输出 {1 1}

	final(&p)
	fmt.Println(p) //期望输出 {2, 2} 但实际输出 {1, 1}
}

为什么`initial`函数修改了指针`final`函数修改了指针的副本

`initial``final`函数的参数都指向`main`函数中`p`的内存地址`initial`成功修改了`p``final`无法修改

如果对此情况有任何解释将不胜感激
英文:
package main

import (
	"fmt"
)

type Numbers struct {
	x int
	y int
}

func initial(number *Numbers) {
	number.x = 1
	number.y = 1
}

func final(number *Numbers) {
	number = &Numbers{2, 2}
}

func main() {
	p := Numbers{0, 0}
	fmt.Println(p) //Prints {0 0}

	initial(&p)
	fmt.Println(p) //Prints {1 1}

	final(&p)
	fmt.Println(p) //Expected to print {2, 2} but prints {1, 1}
}

Why does the initial function modify the pointer, while the final function modifies a copy of the pointer?

Both initial and final's function parameters point to the memory address of p in main; initial manages to change p, while final can't.

Any explanation so as why this is the case would be greatly appreciated.

答案1

得分: 5

要修改指针所指向的数据,你必须对指针进行解引用操作。解引用操作符是 *。然而,在某些情况下,为了方便使用,Go 会隐式地插入解引用操作。例如,number.x = 1 会被翻译为 (*number).x = 1

这种隐式翻译可能会令人困惑,但你应该明白,如果不进行这种翻译,表达式 number.x = 1 就没有意义,因为 number 是一个指针类型,指针没有字段。

所以总结一下,initial 函数具有隐式的指针解引用,而 final 函数则没有。

如果你将 final 修改为显式且正确的解引用操作,即 *number = Numbers{2, 2},那么它也会改变 p

英文:

To modify the data pointed to by a pointer, you must dereference the pointer. The dereference operator is *. However, Go will implicitly insert the dereference operation in some cases for ease of use. For example, number.x = 1 is translated to (*number).x = 1.

This implicit translation may be confusing, but you should see that if it that translation didn't happen, then the expression number.x = 1 would be meaningless, since number is a pointer type and pointers don't have fields.

So in summary, the initial function has implicit pointer dereference, while final does not.

If you changed final to explicitly and correctly dereference, *number = Numbers{2, 2}, then it will also change p.

答案2

得分: 1

initial函数对传递的指针进行操作,该指针指向在main函数中分配的变量。所有的更改都是在main函数中分配的对象上进行的。

final函数接收相同的指针作为参数,然而,它将该指针赋值给另一个Numbers实例。main函数中的对象永远不会改变。

在这两个函数中都没有涉及复制操作。

英文:

The initial function works on the passed pointer, which is pointing to the variable allocated in main. All changes are performed on the object allocated in main.

The final function receives the same pointer as an argument, however, it assigns the pointer to another Numbers instance. The object in main never changes.

There is no copying involved in either function.

huangapple
  • 本文由 发表于 2023年1月4日 05:56:44
  • 转载请务必保留本文链接:https://go.coder-hub.com/74999044.html
匿名

发表评论

匿名网友

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

确定