龙空技术网

golang基础之struct

云计算小哥 158

前言:

当前各位老铁们对“python怎么定义结构体”大约比较看重,看官们都需要分析一些“python怎么定义结构体”的相关资讯。那么小编在网摘上汇集了一些对于“python怎么定义结构体””的相关资讯,希望小伙伴们能喜欢,兄弟们快快来学习一下吧!

一、struct简介

go语言中没有类的定义,但是可以通过结构体struct实现类似java或者python的面向对象编程,struct中的成员可以是任何类型,如普通类型、复合类型、函数、map、interface、struct等。

二、struct定义和初始化

1.struct定义

type struct_variable_type struct {

field1 field_type

field2 field_type

.....

fieldn field_type

}

2.struct初始化

1.通过new(Struct_Name)函数来进行初始化

2.直接使用struct{} 来初始化strut时,返回的是一个struct类型的值

三、struct成员访问控制

在定义struct成员时候区分大小写,若首字母大写则该成员为公有成员(对外可见),否则是私有成员(对外不可见)。

四、struct匿名成员

1.在struct结构体中,不是每个成员都需要有名字的,没有名字的即可成为匿名成员,匿名成员的一个重要作用,可以用来实现oop中的继承。

2.同一种类型匿名成员只允许最多存在一个。

3.当匿名成员是结构体时,且两个结构体中都存在相同字段时,优先选择最近的字段。

package main

import "fmt"

type Person struct {

Name string

Age int

}

type Student struct {

score string

Age int

Person

}

func main() {

var stu = new(Student)

stu.Age = 22 //优先选择Student中的Age

fmt.Println(stu.Person.Age,stu.Age)// 0,22

}

五、struct tag

1.struct tag作用

2.struct tag声明

type User struct {

Id int `json:"id"`

Name string `json:"name"`

Bio string `json:"about,omitempty"` //声明为omitempty后,如果为空, 则生成的json中没有该字段

Admin bool `json:"-"` //-代表不转换,跳过该字段

CreatedAt time.Time `json:"created_at"`

}

3.struct tag获取(通过反射进行获取)

t := reflect.TypeOf(u)

field := t.Elem().Field(0)

fmt.Println(field.Tag.Get("json"))

六、struct继承和多重继承

1.如果一个struct嵌套了另一个匿名结构体,那么这个结构可以直接访问匿名结构体的方法,从而实现继承

2.如果一个struct嵌套了另一个【有名】的结构体,那么这个模式叫做组合

3.如果一个struct嵌套了多个匿名结构体,那么这个结构可以直接访问多个匿名结构体的方法,从而实现多重继承

4.访问父结构中属性也使用“.”,但是当子结构体中存在和父结构中的字段相同时候,只能使用:"子结构体.父结构体.字段"访问父结构体中的属性

5.如果子结构体和父结构体有同名的变量或者函数,并不会产生覆盖,可以通过“父结构名字.变量或函数名”的方式调用父结构体的同名变量或函数

七、struct方法

1.方法和函数的区别

方法和函数的区别在于方法有一个接收者,给一个函数添加一个接收者,那么它就变成了方法。接收者可以是值接收者,也可以是指针接收者。

2.方法定义

func (recv type) methodName(parameter_list) (return_value_list) { … }

3.struct方法之值接收者和指针接收者

(1)实现了接收者是值类型的方法,相当于自动实现了接收者是指针类型的方法;而实现了接收者是指针类型的方法,不会自动生成对应接收者是值类型的方法。

(2)接收者是指针类型的方法,很可能在方法中会对接收者的属性进行更改操作,从而影响接收者;而对于接收者是值类型的方法,在方法中不会对接收者本身产生影响。

(3)如果方法的接收者是值类型,无论调用者是对象还是对象指针,修改的都是对象的副本,不影响调用者;如果方法的接收者是指针类型,则调用者修改的是指针指向的对象本身。

(4)指针类型接收者适用场景:

a)方法能够修改接收者指向的值。

b)避免在每次调用方法时复制该值,在值的类型为大型结构体时,这样做会更加高效。

(5)示例

package main

Import “fmt”

type Goper interface {

printf()

}

type Goper1 struct {

name string

}

type Goper2 struct {

name string

}

func (self *Goper1) printf() {

fmt.Println(self.name)

}

func (self *Goper2) printf() {

fmt.Println(self.name)

}

func main() {

var g1 Goper1

g1 = Goper1{“go1”}

g1.printf()

var g2 Goper2

g2 = Goper2{“go2”}

g2.printf()

}

//上述直接编译会报错,因为违背了上述的第一条,而实现了接收者是指针类型的方法,不会自动生成对应接收者是值类型的方法。而此时的调用g1和g2均是值类型

正确调用方式:

func main() {

var g1 Goper1

g1 = &Goper1{“go1”}

g1.printf()

var g2 Goper2

g2 = &Goper2{“go2”}

g2.printf()

}

八、struct toString

struct实现String方法,即可在fmt打印格式%s的时候自动调用该方法

九、struct内存布局

go中的结构体内存布局和c结构体布局类似,每个成员的内存分布是连续的

标签: #python怎么定义结构体 #java实现结构体 #python之struct详解