赞
踩
这里并没有使用显示的使用implement和实现的接口依赖进行一个绑定。
这里定义了一个Programmer接口,里面有一个方法,并且结构体实现了这个方法。完全看不到显示的继承implement。实现方法要保证方法的签名和返回值都要保持一致,这样就实现了方法绑定在某一个结构上。
这里推荐使用指针的方式,
只要方法签名一样,可以先写这个方法,未来发现很多程序方法是一样的,再去定义interface,即使这种情况下也不需要去改interface的实现,因为在结构体上面不需要添加implements来显示的定义实现某个接口,只要方法签名一样就可以了。
- var (
- str = "Hello Word"
- )
-
- type Programmer interface {
- WriterHelloWord() string
- }
-
- type Person struct {
- }
-
- func (*Person) WriterHelloWord() string {
- return fmt.Sprintf("%s", str)
- }
-
- func main() {
- p := new(Person)
- fmt.Println(p.WriterHelloWord())
- }
usb插槽就是现实中的接口。
你可以把手机,相机,u盘都插在usb插槽上。而不用担心那个插槽是专门插哪个的(对于USB接口来说并不关心插入的是手机还是相机),原因是做usb插槽的厂家和做各种设备的厂家都遵守了统一的规定包括尺寸,排线等等。可以看到一个接口就可以搞定所有的设备。
一个接口可以适配所有的设备
接口的意义|多态:接口可以让代码的耦合性降低,让代码的同性性增强。多态特性主要是通过接口来体现的。
golang的面向对象编程的核心就是接口编程,和其他语言的接口编程还是有一些不一样的地方。
接口可以让代码的耦合性降低,让代码的同性性增强。
这样的设计需求在Golang编程中也是会大量存在的,我曾经说过,一个程序就是一个世界,在现实世界存在的情况,在程序中也会出现,我们用程序来模拟一下前面的应用场景。
按顺序,我们应该讲解多态,但是在讲解多态前,我们需要讲解接口(interface),因为在Golang中,多态特性主要是通过接口来体现的。
第一步:定义接口以及没有实现的方法,定义好接口之后,就可以开始定义结构体了
- type Usb interface {
- //接口里面定义了两个没有实现的方法
- Start() //插入usb就开始工作
- Stop() //拔出usb就停止工作
- }
第二步:定义结构体去实现接口里面的方法
- type Phone struct {
- }
-
- type Camera struct {
- }
-
- //让phone实现usb接口的方法
- func (p Phone) Start(){
- fmt.Println("phone start work")
- }
-
- func (p Phone) Stop() {
- fmt.Println("phone stop work")
- }
-
- //让camera也实现usb接口的方法
- func (c Camera) Start() {
- fmt.Println("camera start work")
- }
-
- func (c Camera) Stop() {
- fmt.Println("camera stop work")
- }
第三步:创建一个空结构体,写一个方法,方法参数类型为接口类型
- type Computer struct {
-
- }
-
- //编写一个方法working,这里可以接受接口类型,Usb这种接口类型
- //只要实现了接口的都可以传递,所谓实现Usb接口就是指实现了Usb接口的所有方法,上面camera和phone都实现了usb接口
- func (c Computer) Working(u Usb) {
- //通过USB接口变量来调用start和stop方法
- u.Start()
- u.Stop()
- }
第四步:使用接口
- computer := Computer{}
- phone := Phone{}
- camera := Camera{}
-
- computer.Working(phone)
- //有没有觉得将手机插入了接口,将phone结构体变量传给了接口Usb
- //接口就会去调用start stopstart stop
- computer.Working(camera)
- type Phone struct {
-
- }
-
- type Camera struct {
-
- }
-
- type Computer struct {
-
- }
-
- type Usb interface {
- //接口里面定义了两个没有实现的方法
- Start() //插入usb就开始工作
- Stop() //拔出usb就停止工作
- }
-
- //让phone实现usb接口的方法
- func (p Phone) Start(){
- fmt.Println("phone start work")
- }
-
- func (p Phone) Stop() {
- fmt.Println("phone stop work")
- }
-
- //让camera也实现usb接口的方法
- func (c Camera) Start() {
- fmt.Println("camera start worker")
- }
-
- func (c Camera) Stop() {
- fmt.Println("camera stop worker")
- }
-
- //编写一个方法working,这里可以接受接口类型,Usb这种接口类型
- //只要实现了接口的都可以传递,所谓实现Usb接口就是指实现了Usb接口的所有方法,上面camera和phone都实现了usb接口
- func (c Computer) Working(u Usb) {
- //通过USB接口变量来调用start和stop方法
- u.Start()
- u.Stop()
- }
-
-
- func main() {
- computer := Computer{}
- phone := Phone{}
- camera := Camera{}
-
- computer.Working(phone) //有没有觉得将手机插入了接口,将phone结构体变量传给了接口Usb,接口就会去调用start stop
- computer.Working(camera)
- }
当去定义接口,要将方法定义好,然后让结构体来实现它,这种就实现了高内聚,低耦合。
上面也有多态的影子,传入phone就知道是phone,传入camera就知道是camera,随着传人参数都类型不同,体现出不同的状态。
interface类型可以定义一组方法,但是这些不需要实现,并且interface不能包含任何变量(在其他编程语言里面接口里面可以包含变量和常量,但是在golang里面接口里面不允许定义变量常量)。到某个自定义类型(比如结构体Phone)要使用的时候,在根据具体情况把这些方法写出来(实现)。
基本语法
- type 接口名 interface{
- method1(参数列表)返回值列表
- method2(参数列表)返回值列表
- }
-
- 实现接口所有方法
- func(t 自定义类型)method1(参数列表)返回值列表{
- //方法实现
-
- func(t 自定义类型)method2(参数列表)返回值列表{
- //方法实现
函数的签名要保持一致
1)接口里的所有方法都没有方法体,即接口的方法都是没有实现的方法。接口体现了程序设计
的多态和高内聚低偶合的思想。(高内聚就是可以将所有的代码写到函数里面去,低耦合就是程序之间依赖降低了)
2)Golang中的接口,不需要显式的实现。只要一个变量,含有接口类型中的所有方法,那么这
个变量就实现这个接口。因此,Golang中没有implement这样的关键字。(没有体现实现的方法属于哪个接口,golang实现接口是基于方法,而不是接口本身的,相当于隐式的实现了接口)
golang里面实现接口是基于方法,而不是基于接口本身的。接口叫什么名字并不关心,只要将里面的方法实现了自然就实现了这个接口。(如果两个接口里面方法相同,那么一个结构体就可以同时实现这Usb1,Usb2两个接口了,并不指定实现哪个接口,只要将方法实现即可!!!)
- type Usb1 interface {
- Start()
- Stop()
- }
-
- type Usb2 interface {
- Start()
- Stop()
- }
(1)第一题是可以的,至于Test01是A接口的还是B接口的其实并不关心,它关心的其实就是你的方法有没有实现。(其实在实现的时候只看方法而不是哪个接口)
(2)第二题其实就是将两个接口继承到C接口里面来了,因为在两个接口里面都有Test01的方法。接口无论继承多少次,都不允许有相同的方法名。所以第二题编译错误,相对于C接口当中有两个相同的Test01方法。
将结构体变量赋值给接口这样会报错,因为结构体指针实现了接口,但是结构体类型并没有实现该接口。
这里注意是结构体类型实现了方法还是结构体类型的指针实现了方法。是两码事!!!
(1)结构体实现了,那么可以结构体类型(语法糖)和结构体指针类型都可以使用该方法
(2)结构体指针实现了和结构体类型没有任何关系,只能结构体指针类型的变量使用。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。