go语言学习-接口
Go语言中虽然没有传统面向对象语言中类、集成的概念,不过提供了接口的支持,可以使用接口来使用一些面向对象的特性。
在 go 语言中,的接口有下面几个特点:
- 可以包含0个或多个方法的签名
- 只定义方法的签名,不包含实现
- 实现接口不需要显式的声明,只需实现相应方法即可
接口的定义
定义方式如下:
type Namer interface {
method1(param_list) return_list
method2(param_list) return_list
...
}
这里的 Namer 就是接口的名字,只要符合标识符的规则即可。不过,通常约定的接口的名字最好以 er, r, able 结尾(视情况而定),这样一眼就知道它是接口。
实现接口
在 go 中实现接口很简单,不需要显式的声明实现了某个接口,想要实现某个接口,只需要实现接口中的所有方法即可。
package main
import "fmt"
import "math"
type Shaper interface {
Area() float32
Circumference() float32
}
type Rect struct {
Width float32
Height float32
}
type Circle struct {
Radius float32
}
func (r Rect) Area() int {
return r.Width * r.Height
}
func (r Rect) Circumference() int {
return 2 * (r.Width + r.Height)
}
func (c Circle) Area() int {
return math.Pi * c.Radius * c.Radius
}
func (c Circle) Circumference() int {
return math.Pi * 2 * c.Radius
}
func main() {
r := Rect{10, 20}
fmt.Printf("Rect w: %f, d: %f, Area: %f, Circumference: %f", r.Width, r.Height, r.Area(), r.Circumference())
c := Circle{5}
fmt.Printf("Circle r: %f, Area: %f, Circumference: %f", c.Radius, c.Area(), c.Circumference())
}
上面我们定义了一个 Shaper 的接口,其中包含两个方法 Area 和 Circumference,分别用来计算面积和周长。然后我们定义了两个结构体 Rect, Circle 并分别实现了这两个方法。但是上面的程序似乎并没有体现出接口和两个实现类型的关系,下面我们将他们关联起来使用:
func showInfo(s Shaper) {
fmt.Printf("Area: %f, Circumference: %f", s.Area(), s.Circumference())
}
注意,这里方法的参数是一个接口类型的,因此我们可以将实现接口的类型的实例传递进去,像下面这样:
r := Rect{10, 20}
showInfo(r)
c := Circle{5}
showInfo(c)
获取实现接口的实际类型
在上面的 showInfo 中我们传入了接口类型的对象,如果将实现了接口的类型传递进去,那么会将实际类型的其他特性掩盖住,因此通常我们会想要获取其真正的类型, 可以使用下面的方法:
func showInfo(s Shaper) {
switch s.(type) {
case Rect:
fmt.Println("This is Rect")
case Circle:
fmt.Println("This is Circle")
}
fmt.Printf("Area: %f, Circumference: %f\n", s.Area(), s.Circumference())
}
另外可以使用类型断言,来判断某一时刻接口是否是某个具体类型
v, ok := s.(Rect) // s 是一个接口类型
如果 s 此时实际上是 Rect 类型,那么会将 s 转换为 Rect 类型,并且 ok 为 true。否则 ok 为 false。
标准库中的常用接口
io.Reader 和 io.Writer
这两个接口定义了实现io功能的基本操作,因此某种类型只要实现了这两个接口就可以进行io操作。
Reader 接口的定义为:
type Reader interface {
Read(p []byte) (n int, err error)
}
仅仅只有这一个方法,Read方法将从数据流中读取 len(p) 个字节的数据到字节数组 p 中,并且返回读取的字节数(即使发生了错误,n也会返回已经读取的字节数)。
我们可能会经常用到的实现了 Reader 接口的对象有: os.Stdin(标准输入), os.File的实例(文件对象)等等, 我们可以对其调用 Read 方法来读取数据。
Writer 接口的定义:
type Writer interface {
Write(p []byte) (n int, err error)
}
Write 将 len(p) 个字节的数据从 p 中写入到基本数据流中。写入的字节数 n(0 <= n <= len(p))以及任何遇到的引起写入提前停止的错误。
类似的实现了 Writer 接口的对象有: os.Stdout, os.Stderr, os.File 等等。可以使用 Write 方法向其中写入数据。
标准库中定义了很多的接口,这里只是简单的提一下,更多内容还是要去查看标准库的文档。
go语言学习-接口的更多相关文章
- go语言学习之路六:接口详解
Go语言没有类和继承的概念,但是接口的存在使得它可以实现很多面向对象的特性.接口定义了一些方法,但是这些方法不包含实现的代码.也就是说这些代码没有被实现(抽象的方法).同时接口里面也不包含变量. 看一 ...
- Go语言学习之路-11-方法与接口
目录 编程方式 go语言对象方法 自定义类型和方法 接收器: 方法作用的目标(类型和方法的绑定) go面向对象总结 方法的继承 go语言接口 为什么要用接口 接口的定义 接口的作用总结 接口的嵌套 空 ...
- 【C语言学习】《C Primer Plus》第1章 概览
学习总结 1.C语言于1972年由贝尔实验室的Dennis Ritchie在与Ken Thompson一起设计UNIX操作系统的时候开发的.的的设计构想来源于Ken Thompson的B语言.Anyw ...
- 足球运动训练心得及经验分析-c语言学习调查
在准备预备作业02之前,我参考娄老师的提示,阅读了<[做中学(Learning By Doing)]之乒乓球刻意训练一年总结>一文. 在文章描述的字里行间,给予我的印象是系统.负责,娄老师 ...
- 20155224聂小益 - 我的技能与C语言学习
20155224聂小益 - 我的技能与C语言学习 预备作业2 ● 你有什么技能比大多人(超过90%以上)更好? 我认为我可能有些技能身边有的人比较少有,但是要是超过90%以上我实在不敢保证.毕竟厉害的 ...
- 有关C语言学习的调查
有关C语言学习的调查 1.Q:你是怎么学习C语言的?(作业,实验,教材,其他),与你的高超技能相比,C语言的学习有什么经验和教训? A:之间在暑假的之后自己有买了一本C PRIME PLUS 来看基本 ...
- 2017-05-4-C语言学习笔记
C语言学习笔记... ------------------------------------ Hello C语言:什么是程序:程序是指:完成某件事的既定方式和过程.计算机中的程序是指:为了让计算机执 ...
- GO语言学习笔记(一)
GO语言学习笔记 1.数组切片slice:可动态增长的数组 2.错误处理流程关键字:defer panic recover 3.变量的初始化:以下效果一样 `var a int = 10` `var ...
- 20165321 学习基础与C语言学习心得
一.技能学习 我其实在小时候学过挺多东西,在我小学的时候,我曾经短时间地学过小提琴.拉丁舞.国画.书法,但是,由于各种原因,都没有继续学习下去.后来,在我小学四年级的时候,我接触到了二胡,于是,我开始 ...
随机推荐
- 数据库操作之整合Mybaties和事务讲解 5节课
1.SpringBoot2.x持久化数据方式介绍 简介:介绍近几年常用的访问数据库的方式和优缺点 1.原始java访问数据库 开发流程麻烦 ...
- JS实现随机背景图片与图片大小变换的效果
经常在网上见一些网站访问一次背景图片改变一次,而且图片的大小不停变换,于是想着自己研究一下. 背景图片可以通过JS的随机数来改变图片的src来实现随机图片,图片的大小变换可以用JS的setInterv ...
- 【Mysql sql inject】【入门篇】SQLi-Labs使用 part 1【01-11】
人员流动性过大一直是乙方公司痛点.虽然试用期间都有岗前学习,但老员工忙于项目无暇带新人成长,入职新人的学习基本靠自己不断摸索.期望看相关文档就可以一蹴而是不现实的.而按部就班的学习又很难短期内将知识有 ...
- sublime3 python 缩进问题
注意,在sublime中可以选择使用空格还是tap进行缩进, 可以宰这里面进行选择: 如果选择了使用tap符进行缩进,再用空格进行缩进,就会报undinent(没有缩进的错误),也可以这样判断,如果有 ...
- Vulcan 基于Meteor的APollO框架 , grapesjs 用于可视化生成Html 页面
Vulcan 基于Meteor的APollO框架 :http://vulcanjs.org/ grapesjs 用于可视化生成Html http://grapesjs.com/
- Android用户界面开发:TabHost
TabHost是整个Tab的容器,包括两部分,TabWidget和FrameLayout.TabWidget就是每个tab的标签,FrameLayout则是tab内容.TabHost的二种实现方式:第 ...
- Android网络通信(7):NFC
Android网络通信之 NFC NFC:近场通信,是一种超近距离的无线通信技术.Android从2.3版本的SDK开始支持基于NFC通信.基于NFC的识别和通信可分为三个步骤:1.Android通过 ...
- Ex 6_26 序列对齐..._第七次作业
- github 推送代码
一.所有更新一起推送 .git init //初始化本地仓库 . git add . //添加全部文件 .git commit -m 'add all the file' //提交修改 .git st ...
- PHP时间类完整实例
<?php header("Content-type:text/html;Charset=utf-8"); class time{ private $year;//年 pri ...