go语言读书笔记-action系列(类型)

用户定义的类型

实际上这里指的就是结构体,go语言中创建结构体的方式与c中基本大同小异,但是go会每次用上一个type 相当于给这个结构体一个命名,这一点不同于c中的用法。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
//go语言写法
type user strut {
name string
email string
ext int
privileged bool
}
//c语言写法
struct user {
char *name;
char *email;
int ext;
bool privileged;
}

当然c也可以用typedef这个关键字 给予别名使用。

但是go中的type 定义的类型会被认定为一个新的类型,比如:

1
type blade int

这个blade会被认为是全新的类型,将int类型赋值给它时会报错,c语言中就仅仅只是个别名的意思,赋值依然可以。

##内置类型
内置类型指的就是数值类型、字符串类型和布尔类型,也就是常说的int,string这类的。因为其是原始类型,所以对其进行增加或者删除都会创建新值,因为其底层结构不共享。
action中举了这样一个例子:

1
2
3
4
5
6
func Trim(s string, cutset string) string{
if s == "" || cutset == ""nc{
return s
}
return TrimFunc(s,makeCutsetFunc(cutset))
}

这个函数对调用者原始的string值的一个副本进行操作,并且返回一个新的string值做副本。字符串就像整数、浮点数和布尔值一样,本质上是一种很原始的数据值,所以在函数或方法内外传递时,要传递字符串的一份副本。

引用类型

go语言中的引用类型有:切片、映射、通道、接口、和函数类型。创建上述类型的变量是共享底层数据结构的。
�由于其底层共享结构,所以不需要通过指针来共享引用类型的值,而通过复制来传递引用。

1
2
3
4
5
6
7
8
9
func (ip IP) MarshalText() ([]byte,error){
if len(ip) == 0{
return []byte(""),nil
}
if len(ip) != IPV4len && len(ip) !=IPv6len{
return nil,erroes.New("invalid IP address")
}
return []byte(ip.String()),nil
}

以上代码,正如预期的那样通过复制来传递引用,从而不需要通过指针来共享引用类型的值。

总结

go语言中的类型大体上就分为这几类,在其作为方法的参数时,创建新的值就用值接收者,否则就用指针。这就是保持传递的一致性。内置类型与引用类型传递的时候,就需要把握其特性再根据传递原则决定如何使用,比如引用类型因为其底层共享结构,就不用传递指针,仅仅传递引用的副本就可以完成修改值的操作,而内置类型就需要指针。