Golang中结构体指针与字符串指针的区别

Golang中结构体指针与字符串指针的区别 大家好! 我是 Golang 的新手。我无法理解并解释这段代码。

type Book struct {
name string
}

func main() {
a := &Book{name: "hehe"}
b := &string("hehe")
fmt.Println(a) // 为什么能工作?
fmt.Println(b) // 为什么会失败?
}

结构体和字符串(指针、变量)在初始化时有什么区别?

谢谢。^^

4 回复

是的,我忽略了这一点。 谢谢,祝您有美好的一天。

更多关于Golang中结构体指针与字符串指针的区别的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html


无法直接获取字符串的指针,但在Go语言中仍然可以获取字符串变量的指针,例如:

	b := string("hehe")
	PointerToStringVar := &b

完整示例请见:https://goplay.space/#aQZ8yWghJ8N

Book{name: "hehe"}

创建一个新的 Book 实例,使用 & 操作符将获得其地址。这里的 Book{...} 是一个构造函数

struct 不是构造函数,而是一个转换表达式。它接受一个现有值("hehe")并尝试将其转换为 string 类型。你不能将引用操作符 & 与转换表达式结合使用。

在Go语言中,结构体指针和字符串指针的初始化方式有本质区别,这解释了为什么你的代码中a能正常工作而b会失败。

结构体指针初始化

  • 使用&Book{name: "hehe"}是合法的,这是Go语言中的复合字面量语法
  • 这会创建一个Book结构体实例,然后立即获取其地址
  • 结构体支持直接取地址操作

字符串指针初始化

  • &string("hehe")是不合法的语法
  • 字符串字面量"hehe"本身已经是一个不可变的字符串值
  • 不能直接对字符串字面量取地址

正确的字符串指针初始化方式:

package main

import "fmt"

type Book struct {
    name string
}

func main() {
    // 结构体指针 - 正确
    a := &Book{name: "hehe"}
    fmt.Println(a) // 输出: &{hehe}
    
    // 字符串指针 - 正确的方式
    str := "hehe"
    b := &str
    fmt.Println(b)  // 输出: 0x14000010250 (内存地址)
    fmt.Println(*b) // 输出: hehe
    
    // 或者使用new函数
    c := new(string)
    *c = "hehe"
    fmt.Println(c)  // 输出: 0x14000010260
    fmt.Println(*c) // 输出: hehe
}

关键区别

  1. 结构体支持&StructType{...}语法直接创建指针
  2. 字符串字面量不能直接取地址,需要先赋值给变量
  3. 字符串是不可变类型,其字面量在编译时确定

底层原理

  • 结构体复合字面量在堆上分配内存,然后返回地址
  • 字符串字面量是编译时常量,存储在只读数据段,不能直接获取其地址

这就是为什么你的原始代码中a能工作而b会编译失败的原因。

回到顶部