go - interface 介面

來源:互聯網
上載者:User
這是一個建立於 的文章,其中的資訊可能已經有所發展或是發生改變。 Interface

1. 概述
  Interface 是一組抽象方法(未具體實現的方法/僅包含方法名參數傳回值的方法)的集合,有點像但又不同於其他程式設計語言中的 interface 。
  如果實現了 interface 中的所有方法,即該類/對象就實現了該介面

2. interface 類型
  格式:
type interfaceName interface {  //方法列表}
  註:
  a. interface 可以被任意對象實現,一個類型/對象也可以實現多個 interface
  b. 方法不能重載,如 eat() eat(s string) 不能同時存在

3. interface 值
  聲明為 interface 類型的變數,可以儲存任何實現了 interface 中所有方法的類型的變數(對象)
  註:類的實值型別傳遞方法會自動產生對應的參考型別傳遞方法,反之不成立

4. interface 組合
  將一個 interface1 嵌入到另一個 interface2 的聲明中
  其作用相當於把 interface1 的函數包含到 interface2 中,但是組合中不同有重複的方法
  註:
  a. 只要兩個介面中的方法列表相同(與順序無關),即為相同的介面,可以相互賦值
  b. interface1 的方法列表屬於另一個 interface2 的方法列表的子集,interface2 可以賦值給 interface1,反之不成立(因為方法缺失),interface2 中的方法會覆蓋 interface1 中同名的方法
  c. 可以嵌入包中的 interface

5. interface 查詢
  通過查詢可以判斷介面它指向的對象是否為某個類型
  通過查詢可以將原本為子集的 interface1 轉為 interface2 類型,即 interface1 就可以調用原本屬於 interface2 專屬的方法
  常見用法:
  if varName2, ok := varName1.(interface2|typeName); ok {    //此時 varName2 的類型由 interface1 轉為 interface2,或者 varName1 不是 typeName 類型的變數  } else {    //不能轉換 interface,或者 varName1 不是 typeName 類型的變數  }
  註:
  a. varName2 儲存 varName1 值,varName1 為 interface 變數, () 中為類型
  b. varName.(type) 用於判斷類型,不能用於 switch 外的邏輯中,此處的 type 關鍵字

樣本程式:
package mainimport "fmt"type Person struct {name stringage int}func (p Person) printMsg() {fmt.Printf("I am %s, and my age is %d.\n", p.name, p.age)}func (p Person) eat(s string) {fmt.Printf("%s is eating %s ...\n", p.name, s)}func (p Person) drink(s string) {fmt.Printf("%s is drinking %s ...\n", p.name, s)}type People interface {printMsg()PeopleEat    //組合PeopleDrink//eat() //不能出現重複的方法}/*//與上面等價type People interface {printMsg()eat()drink()}*/type PeopleDrink interface {drink(s string)}type PeopleEat interface {eat(s string)}type PeopleEatDrink interface {eat(s string)drink(s string)}//以上 Person 類[型]就實現了 People/PeopleDrink/PeopleEat/PeopleEatDrink interface 類型type Foodie struct {name string}func (f Foodie) eat(s string) {fmt.Printf("I am foodie, %s. My favorite food is the %s.\n", f.name, s)}//Foodie 類實現了 PeopleEat interface 類型func main() {//定義一個 People interface 類型的變數p1var p1 Peoplep1 = Person{"Rain", 23}p1.printMsg()           //I am Rain, and my age is 23.p1.drink("orange juice")//print result: Rain is drinking orange juice//同一類可以屬於多個 interface, 只要這個類實現了這個 interface中的方法var p2 PeopleEatp2 = Person{"Sun", 24}p2.eat("chaffy dish")//print result: Sun is eating chaffy dish ...//不同類也可以實現同一個 interfacevar p3 PeopleEatp3 = Foodie{"James"}p3.eat("noodle")//print result: I am foodie, James. My favorite food is the noodle//interface 賦值p3 = p1  //p3 中的方法會被 p1 中的覆蓋p3.eat("noodle")/************************************//*print result                      *//*Rain is eating noodle ...         *//************************************///interface 查詢//將(子集) PeopleEat 轉為 People 類型if p4, ok := p2.(People); ok {p4.drink("water") //調用 People interface 中有而 PeopleEat 中沒有的方法fmt.Println(p4)}/************************************//*print result                      *//*Sun is drink water ...            *//*{Sun 24}                          *//************************************///查詢 p2 是否為 Person 類型變數if p5, ok := p2.(Person); ok {fmt.Println(p5, "type is Person")p5.drink("***")  //此時也可以調用 Person 所有的方法}/************************************//*print result                      *//*{Sun 24} type is Person           *//*Sun is drink *** ...              *//************************************/var p6 PeopleEat = Foodie{"Tom"}if p7, ok := p6.(People); ok {fmt.Println(p7)} else {fmt.Println("Error: can not convert")}//result: Error: can not convertif p8, ok := p6.(Foodie); ok {fmt.Println(p8, "type is Foodie")}//result: {Tom} type is Foodie}

運行結果:
I am Rain, and my age is 23.
Rain is drinking orange juice ...
Sun is eating chaffy dish ...
I am foodie, James. My favorite food is the noodle.
Rain is eating noodle ...
Sun is drinking water ...
{Sun 24}
{Sun 24} type is Person
Sun is drinking *** ...
Error: can not convert
{Tom} type is Foodie

6. 空介面
  空介面,無方法,即 interface{},可以代表任何類型,有點類似於 java 中的 Object 類
  可以作為任何形參和傳回型別,mixed
  例:
//interface{}var i interface{} = 100var s interface{} = "hello"fmt.Printf("i = %d, s = %s\n", i, s)s = ifmt.Printf("i = %d, s = %d\n", i, s)
  結果:
i = 100, s = hello

i = 100, s = 100


著作權聲明:本文為博主原創文章,未經博主允許不得轉載。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.