Golang中结构体指针与变量的对比
Golang中结构体指针与变量的对比
type Point struct {
x_value int
y_value int
}
func changePointX(pt *Point, new_x_value int) {
pt.x_value = new_x_value <-------------------------------------
}
func updateName(n *string) {
*n = "wedge" <-------------------------------------
}
func main() {
point1 := &Point{1, 2}
fmt.Printf("point 1: %v\n", point1)
changePointX(point1, 100)
fmt.Printf("point 1: %v\n", point1)
name := "tifa"
m := &name
updateName(m)
fmt.Println(name)
}
大家好, 我想理解为什么当我想更新一个字符串的值时,我使用:
*n = "wedge"
而当我想更新一个结构体的值时,我使用:
pt.x_value = new_x_value
这里 pt.x 开头没有星号 (*) —— 我认为也应该像这样:
*pt.x_value = new_x_value <— 但这并不工作,而上面的代码是工作的。
我遗漏了什么?
提前非常感谢。
更多关于Golang中结构体指针与变量的对比的实战教程也可以访问 https://www.itying.com/category-94-b0.html
edgarlip:
*pt.x_value
这样做行不通,因为需要括号来覆盖运算符优先级 (*pt).x_value,但 @NobbZ 解释了正确的惯用法。
edgarlip:
*pt.x_value
星号会对 pt.x_value 进行解引用,而 pt.x_value 是一个 int 类型,并非指针。
点操作符/字段访问器在必要时会自动进行解引用。
edgarlip:
但是,想到的是 Go 何时决定需要或不需要解引用,以及基于什么?
如果点号左侧是一个指针,那么为了访问字段,它会被解引用;如果不是,则不会解引用。
根据经验,每当你在 C 语言中使用 -> 时,Go 都会为你解引用。
edgarlip:
能否详细说明为什么圆括号能让这个生效?
因为那样你就强制星号与指针绑定,从而在进行字段访问之前先进行解引用。
在Go语言中,结构体指针和字符串指针的解引用方式不同,这是因为它们的类型特性决定的。让我通过代码示例来解释:
type Point struct {
x_value int
y_value int
}
// 对于结构体指针,Go会自动解引用
func changePointX(pt *Point, new_x_value int) {
// 这里 pt.x_value 是语法糖,等价于 (*pt).x_value
pt.x_value = new_x_value
// 你也可以显式解引用,两种方式都有效
(*pt).x_value = new_x_value + 1
}
// 对于字符串指针,需要显式解引用
func updateName(n *string) {
// 字符串是不可变类型,需要直接修改指针指向的值
*n = "wedge"
// 下面的代码不会工作,因为字符串没有字段
// n.something = "wedge" // 编译错误
}
func main() {
point1 := &Point{1, 2}
fmt.Printf("point 1: %v\n", point1)
changePointX(point1, 100)
fmt.Printf("point 1: %v\n", point1)
name := "tifa"
m := &name
updateName(m)
fmt.Println(name)
// 更多示例
var s string = "cloud"
var p *string = &s
// 字符串指针操作
*p = "aerith" // 正确:修改指针指向的值
fmt.Println(s) // 输出: aerith
// 结构体指针操作对比
point2 := Point{10, 20}
ptr2 := &point2
// 两种方式都可以
ptr2.x_value = 30 // 自动解引用
(*ptr2).y_value = 40 // 显式解引用
fmt.Printf("point2: %v\n", point2) // 输出: {30 40}
}
关键区别:
- 结构体指针:Go提供了语法糖,
pt.x_value会自动解引用为(*pt).x_value - 字符串指针:字符串是基本类型,没有字段,必须使用
*n来解引用修改值
如果你尝试 *pt.x_value,这会被解析为 *(pt.x_value),而 pt.x_value 是一个int值,不能解引用,所以会编译错误。正确的显式写法是 (*pt).x_value,但通常使用简写形式 pt.x_value 即可。

