Golang结构体创建返回不同的内存地址。

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

golang struct creation return different memory addresses

问题

我遇到了一个问题,不明白为什么golang返回了一个不同的内存地址,尽管看起来是相同的结构体(也许它们并不相同,可能是将相同的值复制到另一个内存地址中?)。

以下是代码:

package main

import (
	"fmt"
)

type Creature struct {
	Name    string
	isAlive bool
}

func foo() Creature {
	myCreature := Creature{Name: "dino", isAlive: true}
	fmt.Printf("%p\n", &myCreature)
	fmt.Println(myCreature)
	return myCreature
}

func main() {
	myCreat := foo()
	fmt.Printf("%p\n", &myCreat)
	fmt.Println(myCreat)
}

代码的输出如下:

0xc000004090
{dino true}
0xc000004078
{dino true}

如你所见,内存地址是不同的。为什么呢?
我应该返回一个内存地址吗?

英文:

I'm having trouble understanding why golang returns a different memory address on what appears to be the same struct (maybe it's not, perhaps it copies with the same values to another memory address?).

Here's the code

package main

import (
	"fmt"
)

type Creature struct {
	Name    string
	isAlive bool
}

func foo() Creature {
	myCreature := Creature{Name: "dino", isAlive: true}
	fmt.Printf("%p\n", &myCreature)
	fmt.Println(myCreature)
	return myCreature
}

func main() {
	myCreat := foo()
	fmt.Printf("%p\n", &myCreat)
	fmt.Println(myCreat)
}

The output of the code is the following

0xc000004090
{dino true}
0xc000004078
{dino true}

As you can see, the memory addresses are different. Why?
Should I instead return a memory address?

答案1

得分: 3

我在理解为什么Golang返回了一个不同的内存地址,尽管它看起来是相同的结构体时遇到了困难(也许它并不相同,可能是将相同的值复制到另一个内存地址中了)。

你返回的不是内存地址,而是一个结构体。

正如你所看到的,内存地址是不同的。

因为你返回了一个结构体,并且它被复制到了一个新的结构体中。

如果你想要一个指针,那么是的,你应该返回一个内存地址。

在Go中的规则是,只有在真正需要时才使用指针,比如当你需要修改结构体的值时。不要使用指针是因为你认为它可能更高效。如果你不强制它按照某种方式执行操作,内存优化器可以更高效地完成其工作。

可以参考以下文章:https://medium.com/@vCabbage/go-are-pointers-a-performance-optimization-a95840d3ef85,https://betterprogramming.pub/why-you-should-avoid-pointers-in-go-36724365a2a7,以及其他许多文章。

英文:

> I'm having trouble understanding why golang returns a different memory address on what appears to be the same struct (maybe it's not, perhaps it copies with the same values to another memory address?).

You didn't return a memory address, you returned a struct.

> As you can see, the memory addresses are different.

Because you returned a struct and it was copied to a new one.

> Why? Should I instead return a memory address?

Yes, if you want a pointer then return that.

package main

import (
	"fmt"
)

type Creature struct {
	Name    string
	isAlive bool
}

func foo() *Creature {
	myCreature := Creature{Name: "dino", isAlive: true}
	fmt.Printf("%p\n", &myCreature)
	fmt.Println(myCreature)
	return &myCreature
}

func main() {
	myCreat := foo()
	fmt.Printf("%p\n", myCreat)
	fmt.Println(*myCreat)
}

Playground

The rule in Go is that you only use pointers when you actually need them, when you have to modify a struct's values or something. You should not use pointers because you think it might be more efficient. The memory optimiser can do its work more efficiently if you don't force it to do things one way or another.

See https://medium.com/@vCabbage/go-are-pointers-a-performance-optimization-a95840d3ef85, https://betterprogramming.pub/why-you-should-avoid-pointers-in-go-36724365a2a7, and many more articles.

huangapple
  • 本文由 发表于 2022年8月6日 08:32:47
  • 转载请务必保留本文链接:https://go.coder-hub.com/73256395.html
匿名

发表评论

匿名网友

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

确定