Go的接口

理解Go的接口

在Go中其实更好理解接口的定义,接口就是对一类结构体的规范,属于这个接口的结构体都实现了一些方法
但是在Go中其实是一种隐式的方法,并没有像Java一样用implement的方法去实现一个接口
只要你实现了一个接口的所有方法,那么你就实现了这个接口,其实某种程度上也是Go多态的体现

Go接口的定义方式

// Animal 定义了是Biter又是Sayer的类型
type Animal interface {
	Biter
	Sayer
}

// Biter 定义了一种类型,一种抽象的类型,只要实现了say()这个方法的类型都可以成为sayer类型
type Biter interface {
	// 方法名字(参数) 返回值
	bite()
}

type Sayer interface {
	say()
}

Go中实现一个接口

隐式实现即可

type Dog struct {
}

func (dog Dog) bite() {
	fmt.Println("狗咬人")
}

func (dog Dog) say() {
	fmt.Println("saysaysay!")
}

“多态”

Go说是一种没有多态的语言,但是这也可以理解成多态

func bited(animal Biter) {
	animal.bite()
}

var animal Biter
animal = &Cat{}
bited(animal) // #狗咬人

接口值

接口值是维护了接口动态类型以及接口动态具体值的
如果一个接口类型为空,值也空,它是nil的,但是如果它类型不为空,即使维护的接口值是空的,它也不是nil
在Go中对nil的判断要谨慎,比如slice,它注定不是nil的,就要同时用len(slice)去判断它是否非空

空接口类型判断

空接口的存在很像是Java中的Object,由于它的存在,它可以用在Map里面当Value,也可以作为函数的参数来使用
同时它的类型也要好好处理,不然的话容易出错, 下面这就是接口类型断言的办法
x.(type)

	// 类型断言, 这里会返回结果的,通过OK去判断是不是这个类型
	if ret, ok := x.(Biter); ok {
		fmt.Println(ret)
	} else {
		fmt.Println("", ret)
	}

	switch v := x.(type) {
	case Animal:
		fmt.Println("Animal", v)
	case Biter:
		fmt.Println("Biter", v)
	default:
		fmt.Println("don't know", v)
	}
posted @ 2022-10-09 21:09  azxx  阅读(15)  评论(0编辑  收藏  举报