GO语言基础-04-数据类型-08-结构体[struct](定义结构体、声明结构体变量、结构体赋值、结构体做参数、结构体指针、结构体嵌套、结构体打印)
1. 定义结构体类型
| type 结构体名称 struct { |
| 成员1 类型 |
| 成员2 类型 |
| ... |
| } |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| } |
2. 声明结构体变量
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| } |
| |
| func main() { |
| var xiShu XiShu |
| fmt.Printf("结构体为:%+v",xiShu) |
| |
| } |
示例可见:声明结构体变量之后,结构体不为空,结构体每个成员都为默认值(字串默认值为空,int 默认值为 0)。
3. 赋值
3.1 用结构体赋值
| 结构体名 = 结构体类型{ 成员1: 值1, 成员2: 值2,... } |
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| } |
| |
| func main() { |
| xiShu := XiShu{ |
| ID: 1, |
| Name: "刘备", |
| Age: 28, |
| } |
| |
| fmt.Printf("结构体为:%+v",xiShu) |
| |
| } |
| 结构体为:{ID:1 Name:刘备 Age:28} |
3.2 每个成员分别赋值
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| } |
| |
| func main() { |
| var xiShu XiShu |
| xiShu.Name = "刘备" |
| xiShu.Age = 28 |
| |
| fmt.Printf("结构体为:%+v",xiShu) |
| |
| } |
结果显示
| 结构体为:{ID:0 Name:刘备 Age:28} |
4. 结构体使用
4.1 结构体作参数
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| } |
| |
| |
| func checkAge(info XiShu)(result string) { |
| if info.Age >= 18 { |
| result = info.Name+"是一个成年人" |
| return result |
| }else { |
| info.Name = "小"+info.Name |
| result = info.Name+"还没有长大" |
| return result |
| } |
| } |
| |
| func main () { |
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| } |
| |
| result := checkAge(liuBei) |
| fmt.Println(result) |
| } |
4.2 结构体指针做参数
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| } |
| |
| func checkAge(info *XiShu)(result string) { |
| if info.Age >= 18 { |
| result = info.Name+"是一个成年人" |
| return result |
| }else { |
| info.Name = "小"+info.Name |
| result = info.Name+"还没有长大" |
| return result |
| } |
| } |
| |
| func main () { |
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| } |
| |
| result := checkAge(&liuBei) |
| fmt.Println(result) |
| } |
4.3 二者区别
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| } |
| |
| func IncreaseAge(info XiShu)(age int) { |
| info.Age += 1 |
| fmt.Printf("函数中构体:\t%+v\n",info) |
| age = info.Age |
| return age |
| } |
| |
| func main () { |
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| } |
| fmt.Printf("原结构体:\t%+v\n",liuBei) |
| IncreaseAge(liuBei) |
| |
| fmt.Printf("当前结构体:\t%+v\n",liuBei) |
| } |
结果
| 原结构体: {ID:0 Name:刘备 Age:28 Position:主公} |
| 函数中构体: {ID:0 Name:刘备 Age:29 Position:主公} |
| 当前结构体: {ID:0 Name:刘备 Age:28 Position:主公} |
如上可见,结构体值变化不会影响函数外。
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| } |
| |
| func IncreaseAge(info *XiShu)(age int) { |
| info.Age += 1 |
| fmt.Printf("函数中构体:\t%+v\n",info) |
| age = info.Age |
| return age |
| } |
| |
| func main () { |
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| } |
| fmt.Printf("原结构体:\t%+v\n",liuBei) |
| IncreaseAge(&liuBei) |
| |
| fmt.Printf("当前结构体:\t%+v\n",liuBei) |
| } |
结果:
| 原结构体: {ID:0 Name:刘备 Age:28 Position:主公} |
| 函数中构体: &{ID:0 Name:刘备 Age:29 Position:主公} |
| 当前结构体: {ID:0 Name:刘备 Age:29 Position:主公} |
如上可见,结构体数据彻底放生变化
4.4 本质原因
函数中的形参和函数外的实参内存地址是不同的。
参数传递时,函数中的形参复制了函数外实参的值,函数结束后形参地址将被释放,这些不会对实参造成影响。
我们将实参的地址作为第二个参数传入函数,然后和第一个形参的地址做比较。
| ackage main |
| |
| import ( |
| "fmt" |
| ) |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| } |
| |
| func IncreaseAge(info XiShu,xiShu *XiShu) { |
| fmt.Printf("比较形参和实参地址:") |
| if &info == xiShu { |
| fmt.Println("相同") |
| }else { |
| fmt.Println("不同") |
| } |
| |
| } |
| |
| func main () { |
| |
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| } |
| IncreaseAge(liuBei,&liuBei) |
| } |
结果:
5. 结构体嵌套
5.1 一个结构体作为另一个结构体的成员
1)定义
| type StructName02 struct { |
| …… |
| MemberName StructName01 |
| } |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| Equipment Equipment |
| } |
| |
| type Equipment struct { |
| Arms string |
| Horse string |
| } |
2)赋值和引用
| StructName02.MemberName.StructName01Menber |
用结构体赋值只能使用StructName02.MemberName.StructName01Menber
的方法
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| Equipment: Equipment{ |
| Arms: "双股剑", |
| Horse: "的卢", |
| }, |
| } |
单个赋值语法中两种方法都可以
| liuBei.Equipment.Arms = "双股剑" |
3)完整示例
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| Equipment Equipment |
| } |
| |
| type Equipment struct { |
| Arms string |
| Horse string |
| } |
| |
| |
| func main () { |
| |
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| Equipment: Equipment{ |
| Arms: "双股剑", |
| |
| }, |
| } |
| |
| liuBei.Equipment.Horse = "的卢" |
| fmt.Printf("%+v",liuBei) |
| } |
| {ID:0 Name:刘备 Age:28 Position:主公 Equipment:{Arms:双股剑 Horse:的卢}} |
5.2 直接引入另一个结构体的所有成员
1)定义
| type StructName02 struct { |
| …… |
| StructName01 |
| } |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| Equipment |
| } |
| |
| type Equipment struct { |
| Arms string |
| Horse string |
| } |
2)赋值和引用
| StructName02.StructName01Menber |
或
| StructName02.MemberName.StructName01Menber |
用结构体赋值
只能用StructName02.MemberName.StructName01Menber
的结构,而不能使用StructName02.StructName01Menber
的结构
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| Equipment: Equipment{ |
| Arms: "双股剑", |
| Horse: "的卢", |
| }, |
| } |
如上,不能
写成:
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| Arms: "双股剑", |
| Horse: "的卢", |
| }, |
| } |
StructName02.MemberName.StructName01Menber
的结构和StructName02.StructName01Menber
的结构都可以。
或
| liuBei.Equipment.Arms = "双股剑" |
3)完整示例
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| Equipment |
| } |
| |
| type Equipment struct { |
| Arms string |
| Horse string |
| } |
| |
| |
| func main () { |
| |
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| |
| |
| |
| |
| } |
| |
| liuBei.Arms = "双股剑" |
| |
| liuBei.Equipment.Horse = "的卢" |
| |
| fmt.Printf("%+v",liuBei) |
| } |
| |
| {ID:0 Name:刘备 Age:28 Position:主公 Equipment:{Arms:双股剑 Horse:的卢}} |
注意,虽然Equipment
的成员可以直接引用,但是打印出的结果依然在Equipment
下。
6. 结构体打印
6.1 仅打印值
代码:
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| } |
| |
| func main () { |
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| } |
| |
| fmt.Println(liuBei) |
| } |
结果输出
6.2 打印成员名和值
| fmt.Printf("%+v",StructName) |
代码:
| package main |
| |
| import "fmt" |
| |
| type XiShu struct { |
| ID int |
| Name string |
| Age int |
| Position string |
| } |
| |
| func main () { |
| liuBei := XiShu{ |
| ID: 0, |
| Name: "刘备", |
| Age: 28, |
| Position: "主公", |
| } |
| |
| fmt.Printf("%+v",liuBei) |
| } |
结果输出
| {ID:0 Name:刘备 Age:28 Position:主公} |

【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· AI技术革命,工作效率10个最佳AI工具