Go语言学习之旅--接口

Posted 赵jc

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Go语言学习之旅--接口相关的知识,希望对你有一定的参考价值。

接口

接口

go语言的接口,是一种新的类型定义,它把所有的具有共性的方法定义在一起,任何其他类型只要实现了这些方法就是实现了这个接口。

  • 语法格式
/* 定义接口 */
type interface_name interface 
   method_name1 [return_type]
   method_name2 [return_type]
   method_name3 [return_type]
   ...
   method_namen [return_type]


/* 定义结构体 */
type struct_name struct 
   /* variables */


/* 实现接口方法 */
func (struct_name_variable struct_name) method_name1() [return_type] 
   /* 方法实现 */

...
func (struct_name_variable struct_name) method_namen() [return_type] 
   /* 方法实现*/

  • 举例

下面我定义一个USB接口,有读read和写write两个方法,再定义一个电脑Computer和一个手机Mobile来实现这个接口。

USB接口

type USB interface 
    read()
    write()

Computer结构体

type Computer struct 

Mobile结构体

type Mobile struct 

Computer实现USB接口方法

func (c Computer) read() 
    fmt.Println("computer read...")


func (c Computer) write() 
    fmt.Println("computer write...")

Mobile实现USB接口方法

func (c Mobile) read() 
    fmt.Println("mobile read...")


func (c Mobile) write() 
    fmt.Println("mobile write...")

测试

func main() 
    c := Computer
    m := Mobile

    c.read()
    c.write()
    m.read()
    m.write()

运行结果

func main() 
    c := Computer
    m := Mobile

    c.read()
    c.write()
    m.read()
    m.write()

实现接口必须实现接口中的所有方法

下面我们定义一个OpenClose接口,里面有两个方法open和close,定义个Door结构体,实现其中一个方法。

package main

import "fmt"

type OpenClose interface 
    open()
    close()


type Door struct 


func (d Door) open() 
    fmt.Println("open door...")


func main() 
    var oc OpenClose
    oc = Door // 这里编译错误,提示只实现了一个接口

golang接口值类型接收者和指针类型接收者

这个话题,本质上和方法的值类型接收者和指针类型接收者,的思考方法是一样的,值接收者是一个拷贝,是一个副本,而指针接收者,传递的是指针。
举例
定义一个Pet接口

type Pet interface 
    eat()

定义一个Dog结构体

type Dog struct 
    name string

实现Pet接口(接收者是值类型)

func (dog Dog) eat() 
    fmt.Printf("dog: %p\\n", &dog)
    fmt.Println("dog eat..")
    dog.name = "黑黑"

测试

func main() 
    dog := Dogname: "花花"
    fmt.Printf("dog: %p\\n", &dog)
    dog.eat()
    fmt.Printf("dog: %v\\n", dog)

运行结果

dog: 0xc000046240
dog: 0xc000046250
dog eat..
dog: 花花

从运行结果,我们看出dog的地址变了,说明是复制了一份,dog的name没有变说明,外面的dog变量没有被改变。

将Pet接口改为指针接收者

func (dog *Dog) eat() 
    fmt.Printf("dog: %p\\n", dog)
    fmt.Println("dog eat..")
    dog.name = "黑黑"

再测试

func main() 
    dog := &Dogname: "花花"
    fmt.Printf("dog: %p\\n", dog)
    dog.eat()
    fmt.Printf("dog: %v\\n", dog)

运行结果

dog: 0xc00008c230
dog: 0xc00008c230
dog eat..
dog: &黑黑

golang接口和类型的关系

  1. 一个类型可以实现多个接口
  2. 多个类型可以实现同一个接口(多态)

一个类型实现多个接口

一个类型实现多个接口,例如:有一个Player接口可以播放音乐,有一个Video接口可以播放视频,一个手机Mobile实现这两个接口,既可以播放音乐,又可以播放视频。
定义一个Player接口

type Player interface 
    playMusic()

定义一个Video接口

type Video interface 
    playVideo()

定义Mobile结构体

type Mobile struct 

实现两个接口

func (m Mobile) playMusic() 
    fmt.Println("播放音乐")


func (m Mobile) playVideo() 
    fmt.Println("播放视频")

测试

func main() 
    m := Mobile
    m.playMusic()
    m.playVideo()

运行结果

播放音乐
播放视频

多个类型实现同一个接口

比如,一个宠物接口Pet,猫类型Cat和狗类型Dog都可以实现该接口,都可以把猫和狗当宠物类型对待,这在其他语言中叫做多态

定义一个Pet接口

type Pet interface 
    eat()

定义一个Dog结构体

type Dog struct 

定义一个Cat结构体

type Cat struct 

实现接口

func (cat Cat) eat() 
    fmt.Println("cat eat...")


func (dog Dog) eat() 
    fmt.Println("dog eat...")

测试

func main() 
    var p Pet
    p = Cat
    p.eat()
    p = Dog
    p.eat()

运行结果

cat eat...
dog eat...

golang接口嵌套

接口可以通过嵌套,创建新的接口。例如:飞鱼,既可以飞,又可以游泳。我们创建一个飞Fly接口,创建一个游泳接口Swim,飞鱼接口有这两个接口组成。

飞Flyer接口

type Flyer interface 
    fly()

创建Swimmer接口

type Swimmer interface 
    swim()

组合一个接口FlyFish

type FlyFish interface 
    Flyer
    Swimmer

创建一个结构体Fish

type Fish struct 

实现这个组合接口

func (fish Fish) fly() 
    fmt.Println("fly...")


func (fish Fish) swim() 
    fmt.Println("swim...")

测试

func main() 
    var ff FlyFish
    ff = Fish
    ff.fly()
    ff.swim()

运行结果

fly...
swim...

以上是关于Go语言学习之旅--接口的主要内容,如果未能解决你的问题,请参考以下文章

Go语言学习之旅--接口

Go学习之旅Go语言安装及环境配置教程

Go语言面向函数和接口编程

初识 go 语言:方法,接口及并发

Go方法和接口

Go方法和接口