type关键字
# type关键字
type
是go
语法里的重要而且常用的关键字,type
绝不只是对应于C/C++
中的typedef
.弄清楚type
的使用,容易理解go
语言中的核心概念struct、interface、函数
等的使用.
# 一、类型定义
# 1.1 定义结构体
- 使用
type
可以定义结构体类型
// 1、定义结构体
// 结构体定义
type person struct {
name string //注意后面不能有逗号
age int
}
1
2
3
4
5
6
2
3
4
5
6
# 1.2 定义接口
- 使用
type
可以定义接口类型
type USB interface {
start()
end()
}
1
2
3
4
2
3
4
# 1.3 定义其他的新类型
- 使用
type
,还可以定义新类型
语法:
type 类型名 Type
1
示例代码:
package main
import "fmt"
type myint int
type mystr string
func main() {
var i1 myint
var i2 = 100
i1 = 100
fmt.Println(i1)
//i1 = i2 //cannot use i2 (type int) as type myint in assignment
fmt.Println(i1,i2)
var name mystr
name = "王二狗"
var s1 string
s1 = "李小花"
fmt.Println(name)
fmt.Println(s1)
name = s1 //cannot use s1 (type int) as type mystr in assignment
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
# 1.4 定义函数的类型
Go
语言支持函数式编程,可以使用高阶编程㞏,一个函数可以作为另一个函数的参数,也可以作为另一个函数的返回值,那么在定义这个高阶函数的时候,如果函数的类型比较复杂,就可以使用type
来定义这个函数的类型
package main
import {
"fmt"
"strcov"
}
func main() {
res1 := fun1()
fmt.Println(res1(10,20))
}
type my_fun func(int,int)(string)
//fun1()函数的返回值是`my_func`类型
func fun1() my_fun{
fun := func(a,b int) string {
s := strconv.Itoa(a) + strconv.Itoa(b)
return s
}
return fun
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
# 二、类型别名
类型别名的写法为:
type 别名 = Type
1
类型别名规定: TyepAlias
只是Type
的别名,本质上TypeAlias
与Type
是同一个类型.就像一个孩子小时候有小名、乳名,上学后用学名,英语老师又会给他起英文名,但这些名字都指的是他本人.
类型别名是Go 1.9
版本添加的新功能.主要用于代码升级、迁移中类型的兼容性问题.在C/C++
语言中,代码重构升级可以使用宏快速定义新的一段代码.Go
语言中没有选择加入宏,而是将解决重构中最麻烦的类型名变更问题.
在Go 1.9
版本之前的内建类型定义的代码是这些写的:
type byte uint8
type rune int32
1
2
2
而在Go 1.9
版本之后变为:
type byte = uint8
type rune = int32
1
2
2
这个修改就是配置类型别名而进行的修改.
示例代码:
package main
import (
"fmt"
)
func main() {
var i1 myint
var i2 = 100
i1 = 100
fmt.Println(i1)
//i1 = i2 //cannot use i2 (type int) as type myint int assignment
fmt.Println(i1,i2)
var i3 myint2
i3 = i2
fmt.Println(i1,i2,i3)
}
type myint int
type myint2 = int //不是重新定义类型,只是给int起别名
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
# 三、非本地类型不鞥你定义方法
能够随意为各种类型起名字,是否意味着可以在自己包里为这些类型任意添加方法?
package main
import (
"time"
)
//定义time.Duration的别名为MyDuration
type MyDuration = time.Duration
// 为MyDuration添加一个函数
func (m MyDuration) EasySet(a string) {// cannot define new methods on non-local type time.Duration
}
fun main() {
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
2
3
4
5
6
7
8
9
10
11
12
13
14
15
以上代码报错.报错信息: cannot define new methods on non-local type time.Duration
编译器提示: 不能在一个非本地的类型time.Duration
上定义新方法.非本地方法指的就是使用time.Duration
的代码所在的包,也就是main
包.因为time.Duration
是在time
包中定义的,在main
包中使用.time.Duration
包与main
包不在同一个包中,因此不能为在一个包中的类型定义方法.
解决这个问题有下面两种方法:
- 将类型别名改为类型定义:
type MyDuration time.Duration
,也就是将MyDuration
从别名改为类型. - 将
MyDuration
的别名定义放在time
包中.
# 四、在结构体成员嵌入时使用别名
当类型别名作为结构体嵌套如的成员时会发生什么情况?
package main
import "fmt"
type Person struct {
name string
}
func (p Person) show() {
fmt.Println("Person----->", p.name)
}
//类型别名
type People = Person
func (p People) show1() {
fmt.Println("People----->", p.name)
}
type Student struct {
//嵌入两个结构体
Person
People
}
func main() {
var s Student
//s.name = "王二狗" // ambiguous selector s.name
s.People.name = "王二狗"
//s.show() // ambiguous selector s.show
s.Person.show()
fmt.Printf("%T,%T\n", s.Person, s.People)
s.People.name = "李小花"
s.People.show1()
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
# 五、golang pkg
- https://golang.google.cn/pkg/
- https://golang.google.cn/pkg/time/
上次更新: 2024/04/09, 16:48:42
- 01
- AWS NAT-NetWork-Firwalld配置(一)04-09
- 02
- AWS NAT-NetWork-Firwalld配置(二)04-09
- 03
- kubernetes部署minio对象存储01-18