温馨提示×

温馨提示×

您好,登录后才能下订单哦!

密码登录×
登录注册×
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》

golang语言渐入佳境[18]-interface接口

发布时间:2020-07-09 19:57:12 阅读:207 作者:jonson_jackson 栏目:开发技术
GO开发者专用服务器限时活动,0元免费领,库存有限,领完即止! 点击查看>>

接口声明与定义

interface关键字,在接口中有函数,但是没有实现。

123
type Phone interface {	call()}

例子

一旦有结构体实现了此函数,那么就可以用接口来接收此结构体。

1234567891011121314151617181920212223242526272829303132333435
package mainimport "fmt"type Phone interface {	call()}type AndroidPhone struct {}type IPhone struct {}func (a AndroidPhone) call() {	fmt.Println("我是安卓手机,可以打电话了")}func (i IPhone) call() {	fmt.Println("我是苹果手机,可以打电话了")}func main() {//	定义接口类型的变量var phone Phone	phone = new(AndroidPhone)	phone = AndroidPhone{}	fmt.Printf("%T , %v , %p \n" , phone , phone , &phone)	phone.call()	phone = new(IPhone)	phone = IPhone{}	fmt.Printf("%T , %v , %p \n" , phone , phone , &phone)	phone.call()}

案例2

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081
package mainimport "fmt"type Income interface {	calculate() float64 //计算收入总额	source() string     //用来说明收入来源}//固定账单项目type FixedBilling struct {	projectName  string  //工程项目	biddedAmount float64 //项目招标总额}//定时生产项目(定时和材料项目)type TimeAndMaterial struct {	projectName string	workHours   float64 //工作时长	hourlyRate  float64 //每小时工资率}//固定收入项目func (f FixedBilling) calculate() float64 {return f.biddedAmount}func (f FixedBilling) source() string {return f.projectName}//定时收入项目func (t TimeAndMaterial) calculate() float64 {return t.workHours * t.hourlyRate}func (t TimeAndMaterial) source() string {return t.projectName}//通过广告点击获得收入type Advertisement struct {	adName         string	clickCount     int	incomePerclick float64}func (a Advertisement) calculate() float64 {return float64(a.clickCount) * a.incomePerclick}func (a Advertisement) source() string {return a.adName}func main() {	p1 := FixedBilling{"项目1", 5000}	p2 := FixedBilling{"项目2", 10000}	p3 := TimeAndMaterial{"项目3", 100, 40}	p4 := TimeAndMaterial{"项目4", 250, 20}	p5 := Advertisement{"广告1", 10000, 0.1}	p6 := Advertisement{"广告2", 20000, 0.05}	ic := []Income{p1, p2, p3, p4, p5, p6}	fmt.Println(calculateNetIncome(ic))}//计算净收入func calculateNetIncome(ic []Income) float64 {	netincome := 0.0for _, income := range ic {		fmt.Printf("收入来源:%s ,收入金额:%.2f \n", income.source(), income.calculate())		netincome += income.calculate()	}return netincome}//说明:// 没有对calculateNetIncome函数做任何更改,尽管添加了新的收入方式。全靠多态性而起作用。// 由于新的Advertisement类型也实现了Income接口,可以将它添加到ic切片中。// calculateNetIncome函数在没有任何更改的情况下工作,因为它可以调用Advertisement类型的calculate()和source()方法。

空接口

12
type A interface {}

空接口可以接受任何的数据类型

1234567
type A interface {}var a1 A = Cat{"Mimi", 1}var a2 A = Person{"Steven", "男"}var a3 A = "Learn golang with me!"var a4 A = 100var a5 A = 3.14

定义map。value是任何数据类型

12345
//2、定义map。value是任何数据类型map1 := make(map[string]interface{})map1["name"] = "Daniel"map1["age"] = 13map1["height"] = 1.71

定义一个切片,其中存储任意数据类型

123
slice1 := make([]interface{}, 0, 10)slice1 = append(slice1, a1, a2, a3, a4, a5)fmt.Println(slice1)

完整案例

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455
package mainimport ("fmt")type A interface {}type Cat struct {	name string	age  int}type Person struct {	name string	sex  string}func main() {var a1 A = Cat{"Mimi", 1}var a2 A = Person{"jonson", "男"}var a3 A = "Learn golang with me!"var a4 A = 100var a5 A = 3.14	showInfo(a1)	showInfo(a2)	showInfo(a3)	showInfo(a4)	showInfo(a5)	fmt.Println("------------------")//1、fmt.println参数就是空接口	fmt.Println("println的参数就是空接口,可以是任何数据类型", 100, 3.14, Cat{"旺旺", 2})//2、定义map。value是任何数据类型	map1 := make(map[string]interface{})	map1["name"] = "Daniel"	map1["age"] = 13	map1["height"] = 1.71	fmt.Println(map1)	fmt.Println("------------------")//	3、定义一个切片,其中存储任意数据类型	slice1 := make([]interface{}, 0, 10)	slice1 = append(slice1, a1, a2, a3, a4, a5)	fmt.Println(slice1)}func showInfo(a A) {	fmt.Printf("%T , %v \n", a, a)}

接口对象转型的两种方式

123456789101112131415161718192021222324
//接口对象转型方式1//instance,ok := 接口对象.(实际类型)func getType(s Shape) {if instance, ok := s.(Rectangle); ok {		fmt.Printf("矩形:长度%.2f , 宽度%.2f , ", instance.a, instance.b)	} else if instance, ok := s.(Triangle); ok {		fmt.Printf("三角形:三边分别:%.2f , %.2f , %.2f , ", instance.a, instance.b, instance.c)	} else if instance, ok := s.(Circle); ok {		fmt.Printf("圆形:半径%.2f , ", instance.radius)	}}//接口对象转型——方式2//接口对象.(type),  配合switch和case语句使用func getType2(s Shape) {switch instance := s.(type) {case Rectangle:		fmt.Printf("矩形:长度为%.2f , 宽为%.2f ,\t", instance.a, instance.b)case Triangle:		fmt.Printf("三角形:三边分别为%.2f ,%.2f , %.2f ,\t", instance.a, instance.b, instance.c)case Circle:		fmt.Printf("圆形:半径为%.2f ,\t", instance.radius)	}}

接口对象转型案例 求周长或者面积

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112
package mainimport ("math""fmt")//1、定义接口type Shape interface {	perimeter() float64	area() float64}//2.矩形type Rectangle struct {	a, b float64}//3.三角形type Triangle struct {	a, b, c float64}//4.圆形type Circle struct {	radius float64}//定义实现接口的方法func (r Rectangle) perimeter() float64 {return (r.a + r.b) * 2}func (r Rectangle) area() float64 {return r.a * r.b}func (t Triangle) perimeter() float64 {return t.a + t.b + t.c}func (t Triangle) area() float64 {//海伦公式	p := t.perimeter() / 2 //半周长return math.Sqrt(p * (p - t.a) * (p - t.b) * (p - t.c))}func (c Circle) perimeter() float64 {return 2 * math.Pi * c.radius}func (c Circle) area() float64 {return math.Pow(c.radius, 2) * math.Pi}//接口对象转型方式1//instance,ok := 接口对象.(实际类型)func getType(s Shape) {if instance, ok := s.(Rectangle); ok {		fmt.Printf("矩形:长度%.2f , 宽度%.2f , ", instance.a, instance.b)	} else if instance, ok := s.(Triangle); ok {		fmt.Printf("三角形:三边分别:%.2f , %.2f , %.2f , ", instance.a, instance.b, instance.c)	} else if instance, ok := s.(Circle); ok {		fmt.Printf("圆形:半径%.2f , ", instance.radius)	}}//接口对象转型——方式2//接口对象.(type),  配合switch和case语句使用func getType2(s Shape) {switch instance := s.(type) {case Rectangle:		fmt.Printf("矩形:长度为%.2f , 宽为%.2f ,\t", instance.a, instance.b)case Triangle:		fmt.Printf("三角形:三边分别为%.2f ,%.2f , %.2f ,\t", instance.a, instance.b, instance.c)case Circle:		fmt.Printf("圆形:半径为%.2f ,\t", instance.radius)	}}func getResult(s Shape) {	getType2(s)	fmt.Printf("周长:%.2f ,面积:%.2f \n", s.perimeter(), s.area())}func main() {var s Shape	s = Rectangle{3, 4}	getResult(s)	showInfo(s)	s = Triangle{3, 4, 5}	getResult(s)	showInfo(s)	s = Circle{1}	getResult(s)	showInfo(s)	x := Triangle{3, 4, 5}	fmt.Println(x)}func (t Triangle) String() string {return fmt.Sprintf("Triangle对象,属性分别为:%.2f, %.2f, %.2f", t.a, t.b, t.c)}func showInfo(s Shape) {	fmt.Printf("%T ,%v \n", s, s)	fmt.Println("-------------------")}
  • 本文链接: https://dreamerjonson.com/2018/11/27/golang-18-interface/

  • 版权声明: 本博客所有文章除特别声明外,均采用 CC BY 4.0 CN协议 许可协议。转载请注明出处!

golang语言渐入佳境[18]-interface接口

亿速云「云服务器」,即开即用、新一代英特尔至强铂金CPU、三副本存储NVMe SSD云盘,价格低至29元/月。点击查看>>

向AI问一下细节

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

AI

开发者交流群×