go中的结构体struct
结构体的介绍:
- golang支持面向对象,是基于struct来实现OOP特性的,相当于Java中的class类。
- golang去掉了传统的oop语言的继承,方法重载,构造函数和析构函数,隐藏的this指针。
- golang仍然有面向对象编程的继承,封装和多态的特性。但是golang的继承没有extends关键字,继承是通过匿名字段来实现的。
代码举例:
package model // Cat 定义一个结构体 type Cat struct { Name string Age int Color string Hobby string } package main import ( "fmt" "mygo_code/chapter8/demo08/model" ) func main() { //创建一个cat的变量 var cat model.Cat cat.Name = "小白" cat.Age = 1 cat.Color = "白色" cat.Hobby = "玩耍" fmt.Println("cat=", cat)//cat= {小白 1 白色 玩耍} }
结构体变量在内存的布局
如何声明结构体
type 结构体名称 struct{ type Student struct{ field1 type Name string field2 type -> Age int } }
字段/属性:
基本介绍:字段是结构体的一个组成部分,一般是基本数据类型,数组,也可是引用类型。比如我们前面定义猫结构的Name string就是属性。
细节:
- 字段声明语法同变量,示例:字段名 字段类型。Name string
- 字段的类型可以为:基本类型,数组或引用类型。
- 在创建一个结构体变量后,如果没有给字段赋值,都对应一个零值(默认值)。指针,slice,和map的零值都是nil,即还没有分配空间。
- 不同的结构体变量的字段是独立的,互不影响,一个结构体变量的字段的更改,不影响另外一个,结构体是值类型。
var m1 model.Monster m1.Name = "小怪兽" m1.Age = 500 m2 := m1 //这里其实把m1的值拷贝了一份给m2 m2.Name = "大怪兽" fmt.Println("m1=", m1) //m1的Name没有被修改 因为结构体是值类型 fmt.Println("m2=", m2)
创建结构体的方式
func main() { //创建结构体的方法1 var person model.Person //定义一个Person结构体 person.Name = "张三" //给结构体赋值 person.Age = 18 //给结构体赋值 fmt.Println("person=", person) //创建结构体的方法2 person2 := model.Person{ Name: "李四", Age: 19, } fmt.Println("person2=", person2) //创建结构体的方法3 var person3 *model.Person = new(model.Person) //使用new函数创建结构体 返回的是结构体的指针 (*person3).Name = "王五" //因为person3是指针,所以需要使用*person3来访问结构体的属性 person3.Age = 20 //也可以这样使用 go的设计者为了简化代码,提供了这种简写形式 fmt.Println("person3=", *person3) //person3是指针,所以需要使用*person3来访问结构体的属性 //创建结构体的方法4 person4 := &model.Person{ Name: "赵六", Age: 21, } //使用&符号创建结构体,返回的是结构体的指针 fmt.Println("person4=", *person4) //person4是指针,所以需要使用*person4来访问结构体的属性 }
- 第三种和第四种方式返回的是结构体的指针。
- 结构体指针访问字段的标准格式是:(结构体指针名).属性名,比如 (person3).Name = "王五"。
- go的设计者为了简化代码,提供了这种简写形式,比如 person3.Name = "王五"也可以。go的编译器对person3.Name做了转化为(*person3).Name。
结构体的注意事项和细节
- 结构体的所有字段在内存中是连续的。
- 结构体是用户单独定义的类型,和其他类型进行转换时需要有完全相同的字段(包括名字,个数和类型)。
- 结构体进行type重新定义(相当于别名),GOLANG中认为是新的数据类型,但是相互间可以强转。
- struct每个字段上,可以写一个tag,该tag可以通过反射机制获取,常见的使用场景就是序列化和反序列化。
type Monster struct { Name string `json:"name"` //这里就是tag标签 Age int `json:"age"` Skill string `json:"skill"` } func main() { monster := model.Monster{Name: "牛魔王", Age: 2000, Skill: "八角拳"} //把monster进行序化为json格式 marshal, err := json.Marshal(monster) if err != nil { fmt.Println("json处理错误", err) } fmt.Println(string(marshal))//{"name":"牛魔王","age":2000,"skill":"八角拳"} }
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 展开说说关于C#中ORM框架的用法!