go 函数和方法的区别

说明#

函数是没有接收者的;而方法是有接收者的。Go语言不像其它面相对象语言一样可以写个类,然后在类里面写一堆方法,但其实Go语言的方法很巧妙的实现了这种效果:我们只需要在普通函数前面加个接受者(receiver,写在函数名前面的括号里面),这样编译器就知道这个函数(方法)属于哪个struct了

函数是没有接收者的;而方法是有接收者的,我们说的方法要么是属于一个结构体的,要么属于一个新定义的类型的。

方法的声明和函数类似,他们的区别是:方法在定义的时候,会在func和方法名之间增加一个参数,这个参数就是接收者,这样我们定义的这个方法就和接收者绑定在了一起,称之为这个接收者的方法。

1
2
3
4
5
6
7
type person struct {
name string
}

func (p person) String() string{
return "the person name is "+ p.name
}

在 Go 中,(接收者)类型关联的方法不写在类型结构里面,就像类那样;耦合更加宽松;类型和方法之间的关联由接收者来建立。 Go 语言不像其它面相对象语言一样可以写个类,然后在类里面写一堆方法,但其实**Go语言的方法**很巧妙的实现了这种效果:我们只需要在普通函数前面加个接受者(receiver,写在函数名前面的括号里面),这样编译器就知道这个函数(方法)属于哪个struct了

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
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
import (
"fmt"
)

func StructTest06Base() {
structTest0601()
structTest0602()
}

//1.普通函数
//接收值类型参数的函数
func valueIntTest(a int) int {
return a + 10
}

//接收指针类型参数的函数
func pointerIntTest(a *int) int {
return *a + 10
}

func structTest0601() {
a := 2
fmt.Println("valueIntTest:", valueIntTest(a))
//函数的参数为值类型,则不能直接将指针作为参数传递
//fmt.Println("valueIntTest:", valueIntTest(&a))
//compile error: cannot use &a (type *int) as type int in function argument

b := 5
fmt.Println("pointerIntTest:", pointerIntTest(&b))
//同样,当函数的参数为指针类型时,也不能直接将值类型作为参数传递
//fmt.Println("pointerIntTest:", pointerIntTest(b))
//compile error:cannot use b (type int) as type *int in function argument
}

//2.方法
type PersonD struct {
id int
name string
}

//接收者为值类型
func (p PersonD) valueShowName() {
fmt.Println(p.name)
}

//接收者为指针类型
func (p *PersonD) pointShowName() {
fmt.Println(p.name)
}

func structTest0602() {
//值类型调用方法
personValue := PersonD{101, "Will Smith"}
personValue.valueShowName()
personValue.pointShowName()

//指针类型调用方法
personPointer := &PersonD{102, "Paul Tony"}
personPointer.valueShowName()
personPointer.pointShowName()

//与普通函数不同,接收者为指针类型和值类型的方法,指针类型和值类型的变量均可相互调用
}