Go语言基础十四——方法

225 阅读3分钟

我正在参加「掘金·启航计划」

Go 语言中 的方法 ( Method ) 是一种作用 于特定类型变量 的函数 。这种特定类型变量 叫做接收器( Receiver ) 。 如果将特定类型理解为结构体或“类”时,接收器的概念就类似于其他语言中的 this 或 者 self。 在 Go 语言中,接收器的类型可以是任何类型,不仅仅是结构体,任何类型都可以拥有方法。

简单的说,我们可以给任何类型(包含内置类型)添加方法 方法必须和特定的数据类型绑定才能使用,也就是说方法一定会有一个自己的接收器,接收器就是指定的数据类型,或者也可以称为一个实例 方法和函数的区别是,函数没有作用对象,即不需要和特定的数据类型变量绑定.

1、定义

golang方法总是绑定对象实例,并隐式将实例作为第一个实参(receiver).

一个方法就是一个包含了接收者的函数,接收者可以是命名类型或者结构体类型的一个值或者一个指针。

所有给定类型的方法属于该类型的方法集。

  • 只能为当前包内命名类型定义方法。
  • 参数receiver可任意命名。如方法中未曾使用,可省略参数名。
  • 参数receiver类型可以是T或*T,基本类型T不能是接口或指针。
  • 不支持方法重载,receiver只是参数签名的组成部分。
  • 可用示例value或pointer调用全部方法,编译器自动转换
func (receiver type) methodName(参数列表) (返回值列表) {}

参数和返回值可以省略
示例:

type Test struct{}

func (t Test) m1(){

}

func (t *Test) m2(){
}

方法更多的时候是和结构体一起,构成面向对象编程

package main 
import "fmt" 

type Animal struct {
    name string 
    hobby []string 
}

func NewAnimal(name string,hobby []string) *Animal{
	return  &Animal{
		name:name,
		hobby:hobby,
	}
}
// Animal类型绑定的方法
func (a Animal) SelfIntroduction(){
	hobbys := ""
	for _,h := range a.hobby{
		hobbys = hobbys+h+" "
	}
	fmt.Printf("我是 %s 爱好是 %s\n",a.name,hobbys)
}
// Animal类型绑定的方法不同的是接收器是指针类型的Animal类型,引用传递
// 此处的是指针接收器,对原值有影响
func (a *Animal) addHobby(h string){
	a.hobby = append(a.hobby,h)
}

func main() {
	// 初始化一个animal类型的实例 p1
	p1 := NewAnimal("dog",[]string{"汪汪汪"})
	// 调用方法
	p1.SelfIntroduction()
	p1.addHobby("骨头")
	p1.SelfIntroduction()
	// 初始化一个结构体变量 a2 (换一种说法)
	// p1 和 p2 在内存中有相同的布局,但是本质上是两个内存空间,毫不相关
	p2 := NewAnimal("Anne",[]string{"汪汪汪","骨头"})
	p2.SelfIntroduction()
}

2、指针接收器与非指针接收器

由于指针的特性,修改指针接收器的任意成员,在方法调用结束之后,会对原有的数据产生效果 而非指针接收器是值拷贝一份,方法内修改接收器的成员,在方法结束之后不影响原有值

  • 数据量小的对象赋值比较快,使用非指针接收器也合适,数据量大的对象赋值起来性能较低,使用指针接收器比较合适,

3、方法和函数的区别:

  • 对于普通函数,接收者为值类型时,不能将指针类型的数据直接传递,反之亦然。
  • 对于方法,接收者为值类型时,可以直接用指针类型的变量调用方法,反过来也可以。