Go: 复合数据类型struct
结构体
结构体是将零个或多个任意类型的命名变量组合在一起的聚合数据类型。每个变量都叫做结构体的成员。
type Employee struct {
ID int
Name string
age int
}
Employee
就是一个结构体。
定义结构体时要注意
1.如果一个成员变量的首字母大写,则它是可导出的。
2.成员变量的顺序对于结构体的同一性很重要,顺序不同表示不同的结构体。
3.结构体中的成员变量类型不能是结构体本身,但可以是该结构体的指针类型
type Node struct {
value int
next *Node
//这样是非法的
//next Node
}
4.结构体的零值由结构体成员的零值构成。
结构体变量的声明
type Point struct {
X int
Y int
}
// 方式一
p1 := Point{1, 2} // X=1 Y=2
// 方式二
p2 := Point{X: 3, Y: 4} // X=3 Y=4
// 如果某个成员变量没有指定,那么该成员变量的值为该类型零值
p3 := Point{Y:6} // X=0 Y=6
方式一和方式二不可以混用。并且不能通过方式一绕过不可导出变量无法在其他包中使用的规则
。
// p.go
package p
type T struct { a, b int }
// q.go
package q
import "p"
var _ = p.T{1, 2} // 编译错误
var _ = p.T{a: 1, b: 2} // 编译错误
如果在函数中需要修改结构体变量的内容时,需要传递指针
type Point struct {
X, Y int
}
func update(p Point, x int) { // 函数接收到的是实惨的一个副本
p.X = x
}
func update2(p *Point, x int) {
p.X = 2
}
func main() {
p := Point{}
update(p, 1)
fmt.Println(p) // {0 0}
update2(&p, 2)
fmt.Println(p) // {2 2}
}
结构体的比较
必须所有的成员变量是可比较的,那这个结构体是可变比较
type Point struct {
X, Y int
}
type Book struct {
name string
chapters []string
}
func main() {
p1 := Point{X: 1, Y: 2}
p2 := Point{X: 1, Y: 2}
p3 := Point{X: 1, Y: 3}
fmt.Println(p1 == p2, p2 == p3) // true false
b1 := Book{name: "abc", chapters: []string{"1", "2"}}
b2 := Book{name: "abc", chapters: []string{"1", "2"}}
fmt.Print(b1 == b2) // 编译错误,无法比较,因为chapters是slice类型 不能比较
}
结构体嵌套和匿名成员
结构体嵌套的目的是为了复用
Go允许我们定义不带名称的结构体成员(即匿名成员),这样可以快捷访问到匿名成员里的成员变量
type Point struct {
X, Y int
}
type Circle struct {
Point
Radius int
}
type Wheel struct {
Circle
Spokes int
}
func main() {
var w Wheel
w.X = 8 // 等价于w.Circle.Point.X
w.Y = 8
w.Radius = 5 // 等价于w.Circle.Radius
w.Spokes = 20
fmt.Printf("%#v", w) // main.Wheel{Circle:main.Circle{Point:main.Point{X:8, Y:8}, Radius:5}, Spokes:20}
}
外围的结构体Wheel
不仅获得匿名成员Circle
的内部成员变量,也会获得Circle
的方法
type Point struct {
X, Y int
}
func (p Point) Print() {
fmt.Printf("%#v", p)
}
type Circle struct {
Point
Radius int
}
func (c Circle) Print() {
fmt.Printf("%#v", c)
}
type Wheel struct {
Circle
Spokes int
}
// func (w Wheel) Print() {
// fmt.Printf("%#v", w)
// }
func main() {
var w Wheel
w.X = 8
w.Y = 8
w.Radius = 5
w.Spokes = 20
fmt.Printf("%#v\n", w) // main.Wheel{Circle:main.Circle{Point:main.Point{X:8, Y:8}, Radius:5}, Spokes:20}
w.Print() // main.Circle{Point:main.Point{X:8, Y:8}, Radius:5}
}
如果在Wheel
上再加一个匿名命名成员Band
, 它也有Print
方法
type Band struct {
Name string
}
func (b Band) Print() {
fmt.Printf("%#v", b)
}
type Wheel struct {
Circle
Band
Spokes int
}
func main() {
var w Wheel
w.X = 8
w.Y = 8
w.Radius = 5
w.Spokes = 20
fmt.Printf("%#v\n", w) // main.Wheel{Circle:main.Circle{Point:main.Point{X:8, Y:8}, Radius:5}, Band:main.Band{Name:""}, Spokes:20}
w.Print() // 编译报错
w.Circle.Print() // main.Circle{Point:main.Point{X:8, Y:8}, Radius:5}
w.Band.Print() // main.Band{Name:""}
}
如果外围结构体Wheel
有Print
方法,会直接调用该方法;如果没有,但其内部的多个匿名成员都有该方法,需要显示指定调用哪个匿名结构体的Print
方法
Go: 复合数据类型struct的更多相关文章
- hive的复合数据类型
hive中的复合数据类型 Array array中的数据为相同类型,例如,假如array A中元素['a','b','c'],则A[1]的值为'b' 数据结构如下: zhangsan beijing, ...
- C/C++知识总结 五 复合数据类型 壹(数组、字符串与string、结构)
C/C++复合数据类型 壹(数组.结构) 数组 数组的意义.定义与创建 一.二维数组应用 字符数组与字符串处理函数 数组与指针---关系密切 数组的意义与定义创建 意义:反映数据间的特点(通过把同一类 ...
- Verilog缺少一个复合数据类型,如C语言中的结构体
https://mp.weixin.qq.com/s/_9UsgUQv-MfLe8nS938cfQ Verilog中的数据类型(Data Type)是分散的,缺少一个复合数据类型:把多个wire, r ...
- ElasticSearch入门 第六篇:复合数据类型——数组,对象和嵌套
这是ElasticSearch 2.4 版本系列的第六篇: ElasticSearch入门 第一篇:Windows下安装ElasticSearch ElasticSearch入门 第二篇:集群配置 E ...
- [日常] Go语言圣经--复合数据类型,数组习题
go语言圣经-复合数据类型 1.以不同的方式组合基本类型可以构造出来的复合数据类型 2.四种类型——数组.slice.map和结构体 3.数组是由同构的元素组成——每个数组元素都是完全相同的类型——结 ...
- 【Oracle】Oracle中复合数据类型
1,常见的操作数据库的技术有那些 jdbc 使用java 访问数据库的技术 PLSQL (procedure 过程化sql) 在数据库内部操作数据的技术 proc/c++ ...
- Go语言入门篇-复合数据类型
复合数据类型 主要讨论四种类型——数组.slice.map和结构体 数组和结构体聚合类型 --数组和结构体都是有固定内存大小的数据结构 --数组:由同构的元素组成——每个数组元素都是完全相同的类型 ...
- Chisel3 - 复合数据类型
https://mp.weixin.qq.com/s/rXYqiZKuBpAYL8R94zxgRA Chisel允许用户根据需要,把基本数据类型组合成为复合数据类型使用.如C语言里面的结构体,这样 ...
- Golang入门教程(九)复合数据类型使用案例二
参考:http://www.runoob.com/go/go-slice.html 目录 切片 字典(map) 函数(func) 接口(interface) 通道(chan) 四.切片(Slice) ...
随机推荐
- 规模化敏捷LeSS(二):LeSS*队实践指南
Scrum 能够帮助一个5-9人的小*队以迭代增量的方式开发产品,在每一迭代结束时,交付潜在的可交付的产品增量.正是由于其灵活性,Scrum 方法现已成为*队软件交付方法的首选,近期发布的15届敏捷状 ...
- [编译] 8、在Linux下搭建 stm8 单片机的开发烧写环境(makefile版)
目录 一.SDCC(Small Device C Compiler)编译环境搭建 1.1.下载 1.2.编译 1.3.测试 二.Hex2Bin+命令行烧写工具配置使用 2.1.下载工具安装配置 2.2 ...
- vscode配置java+gradle开发环境
1.安装扩展包Java Extension Pack,里面包含java开发所必须的扩展 2.安装java jdk,8版本就是1.8版本,根据需要安装不同的版本 3.下载gradle,将bin文件夹添加 ...
- 官宣|VS Code 1.59 发布!Terminal 可以跨窗口移动了!
欢迎使用 2021 年 7 月版的 Visual Studio Code.我们希望您会喜欢此版本中的许多更新与改进,以下是其中的一些高亮: 扩展视图的改进 - 丰富的扩展详细信息悬停,新的运行状态标签 ...
- 我为什么选Markdown
前沿说明:Yaml Front Matter MarkDown 目录 前沿说明:Yaml Front Matter 什么是MarkDown Markdown是一种轻量级标记语言, 它允许人们使用易读易 ...
- Java基础——逻辑运算符、位运算符
逻辑运算符.位运算符.三元运算符 逻辑运算符 public class Demon05 { public static void main(String[] args) { ...
- Mol Cell丨吕志民团队揭示琥珀酰化介导的肿瘤细胞氧化应激调控新机制
蛋白质琥珀酰化修饰 (succinylation) ,作为赖氨酸酰化修饰家族的重要一员,于2011年由芝加哥大学赵英明教授团队在Nature Chemical Biology 发文被首次报道,并被评为 ...
- Android Jetpack 架构组件最佳实践之“网抑云”APP
背景 近几年,Android 相关的新技术层出不穷.往往这个技术还没学完,下一个新技术又出来了.很多人都是一脸黑人问号? 不少开发者甚至开始哀嚎:"求求你们别再创造新技术了,我们学不动了!& ...
- Android茫茫半年求职路,终于斩获三个大厂offer
前言 2019年底,公司出现危机,开始"优化",本组一个小兄弟被"优化",于是我也着手开始做准备,将来若轮到我被"优化",出去面试时也好打个 ...
- 单机版搭建kubernetes(K8s)
准备 云原生的概念越来越火,忍不住去看了看kubernetes,初次接触,晕晕乎乎的,于是不管三七二十一,先搭建个单机版的再说(没钱买服务器,目前也懒得装虚拟机),跑起来也算是第一步吧.网上教程一顿搜 ...