有没有人能解释一下为什么&c1.name在函数中更改后的地址是相同的changeMe()。我认为字符串在 Go 中是不可变的。package mainimport "fmt"type customer struct { name string age int}func main() { c1 := customer{"Todd", 44} fmt.Println(&c1.name) // 0x8201e4120 changeMe(&c1) fmt.Println(c1) // {Rocky 44} fmt.Println(&c1.name) // 0x8201e4120}func changeMe(z *customer) { fmt.Println(z) // &{Todd 44} fmt.Println(&z.name) // 0x8201e4120 z.name = "Rocky" fmt.Println(z) // &{Rocky 44} fmt.Println(&z.name) // 0x8201e4120}
1 回答
catspeake
TA贡献1111条经验 获得超0个赞
字符串的不变性与变量的不变性不同。
字符串的不变性意味着字符串中的字符不能改变。这适用于 Go。Go 在对字符串进行切片时会使用它,如下例所示。
Go 中的变量总是可变的。更改字符串变量时,变量的内部字段(指针和长度)也会更改。变量的地址永远不会改变。
下面的例子展示了 Go 字符串变量的内部结构。第一个整数是字符数组的地址,第二个是长度。
请参阅 Go http://research.swtch.com/godata 中有关字符串内部结构的文章。
package main
import (
"fmt"
"reflect"
"unsafe"
)
func main() {
var x string = "abc"
fmt.Println(x, &x, (*reflect.StringHeader)(unsafe.Pointer(&x)))
x = "cde"
fmt.Println(x, &x, (*reflect.StringHeader)(unsafe.Pointer(&x)))
x = x[1:]
fmt.Println(x, &x, (*reflect.StringHeader)(unsafe.Pointer(&x)))
}
添加回答
举报
0/150
提交
取消