一区二区三区三上|欧美在线视频五区|国产午夜无码在线观看视频|亚洲国产裸体网站|无码成年人影视|亚洲AV亚洲AV|成人开心激情五月|欧美性爱内射视频|超碰人人干人人上|一区二区无码三区亚洲人区久久精品

0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫(xiě)文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

如何實(shí)現(xiàn)implements ?

冬至子 ? 來(lái)源:洋芋土豆 ? 作者:真沒(méi)什么深度 ? 2023-05-22 17:30 ? 次閱讀

概述

Go 中檢測(cè)一個(gè)類(lèi)型是否實(shí)現(xiàn)了某個(gè)接口,通常分為兩類(lèi)機(jī)制: 編譯期間運(yùn)行期間。

編譯期間

顧名思義,編譯期間檢測(cè)就是通過(guò)靜態(tài)分析來(lái)確定類(lèi)型是否實(shí)現(xiàn)了某個(gè)接口,如果檢測(cè)不通過(guò),則編譯過(guò)程報(bào)錯(cuò)并退出。通常將這種方式稱(chēng)為 接口完整性檢查

接口完整性檢查

類(lèi)型未實(shí)現(xiàn)接口

package main

type Person interface {
    Name() string
    Age() int
}

type Martian struct {
}

func main() {
    // 強(qiáng)制類(lèi)型 Martian 必須實(shí)現(xiàn)接口 Person 的所有方法
    var _ Person = (*Martian)(nil)

    // 1. 聲明一個(gè) _ 變量 (不使用)
    // 2. 把一個(gè) nil 轉(zhuǎn)換為 (*Martian),然后再轉(zhuǎn)換為 Person
    // 3. 如果 Martian 沒(méi)有實(shí)現(xiàn) Person 的全部方法,則轉(zhuǎn)換失敗,編譯器報(bào)錯(cuò)
}

運(yùn)行代碼

$ go run main.go
# 輸出如下 
cannot use (*Martian)(nil) (value of type *Martian) as type Person in variable declaration:
        *Martian does not implement Person (missing Age method)

從輸出的結(jié)果中可以看到,Martian 并沒(méi)有實(shí)現(xiàn) Person 接口,所以報(bào)錯(cuò)了。下面我們?yōu)?Martian 實(shí)現(xiàn) Person 接口。

類(lèi)型實(shí)現(xiàn)了接口

package main

import "fmt"

type Person interface {
    Name() string
    Age() int
}

type Martian struct {
}

// 實(shí)現(xiàn) Name 方法
func (m *Martian) Name() string {
    return "martian"
}

// 實(shí)現(xiàn) Age 方法
func (m *Martian) Age() int {
    return -1
}

func main() {
    // 此時(shí) Martian 已實(shí)現(xiàn)了 Person 的全部方法
    var _ Person = (*Martian)(nil)

    m := &Martian{}
    fmt.Printf("name = %s, age = %d\\n", m.Name(), m.Age())
}

運(yùn)行代碼

$ go run main.go
# 輸出如下 
name = martian, age = -1

從輸出的結(jié)果中可以看到,運(yùn)行成功,Martian 已經(jīng)實(shí)現(xiàn)了 Person 接口的全部方法。

運(yùn)行期間

運(yùn)行期間的檢測(cè)方式主要有 類(lèi)型斷言反射

類(lèi)型斷言

類(lèi)型未實(shí)現(xiàn)接口

package main

import "fmt"

type Person interface {
    Name() string
    Age() int
}

type Martian struct {
}

func main() {
    // 變量必須聲明為 interface 類(lèi)型
    var m interface{}
    m = &Martian{}
    if v, ok := m.(Person); ok {
        fmt.Printf("name = %s, age = %d\\n", v.Name(), v.Age())
    } else {
        fmt.Println("Martian does not implements Person")
    }
}

運(yùn)行代碼

$ go run main.go
# 輸出如下 
Martian does not implements Person

下面我們?yōu)?Martian 實(shí)現(xiàn) Person 接口。

類(lèi)型實(shí)現(xiàn)了接口

package main

import "fmt"

type Person interface {
    Name() string
    Age() int
}

type Martian struct {
}

func (m *Martian) Name() string {
    return "martian"
}

func (m *Martian) Age() int {
    return -1
}

func main() {
    // 變量必須聲明為 interface 類(lèi)型
    var m interface{}
    m = &Martian{}
    if v, ok := m.(Person); ok {
        fmt.Printf("name = %s, age = %d\\n", v.Name(), v.Age())
    }
}

運(yùn)行代碼

$ go run main.go
# 輸出如下 
name = martian, age = -1

從輸出的結(jié)果中可以看到,運(yùn)行成功,Martian 已經(jīng)實(shí)現(xiàn)了 Person 接口的全部方法。

反射

通過(guò) reflect 包提供的 API 來(lái)判斷類(lèi)型是否實(shí)現(xiàn)了某個(gè)接口。

類(lèi)型未實(shí)現(xiàn)接口

package main

import (
    "fmt"
    "reflect"
)

type Person interface {
    Name() string
    Age() int
}

type Martian struct {
}

func main() {
    // 獲取 Person 類(lèi)型
    p := reflect.TypeOf((*Person)(nil)).Elem()

    // 獲取 Martian 結(jié)構(gòu)體指針類(lèi)型
    m := reflect.TypeOf(&Martian{})

    // 判斷 Martian 結(jié)構(gòu)體類(lèi)型是否實(shí)現(xiàn)了 Person 接口
    fmt.Println(m.Implements(p))
}

運(yùn)行代碼

$ go run main.go
# 輸出如下 
false

下面我們?yōu)?Martian 實(shí)現(xiàn) Person 接口。

類(lèi)型實(shí)現(xiàn)了接口

package main

import (
    "fmt"
    "reflect"
)

type Person interface {
    Name() string
    Age() int
}

type Martian struct {
}

func (m *Martian) Name() string {
    return "martian"
}

func (m *Martian) Age() int {
    return -1
}

func main() {
    // 獲取 Person 類(lèi)型
    p := reflect.TypeOf((*Person)(nil)).Elem()

    // 獲取 Martian 結(jié)構(gòu)體指針類(lèi)型
    m := reflect.TypeOf(&Martian{})

    // 判斷 Martian 結(jié)構(gòu)體類(lèi)型是否實(shí)現(xiàn)了 Person 接口
    fmt.Println(m.Implements(p))
}

運(yùn)行代碼

$ go run main.go
# 輸出如下 
true

小結(jié)

Go 的接口實(shí)現(xiàn)檢測(cè)機(jī)制分為 編譯期間運(yùn)行期間,其中編譯期間的檢測(cè)方式是 接口完整性檢查, 而運(yùn)行期間的檢測(cè)方式有兩種: 類(lèi)型斷言反射,一般情況盡量使用類(lèi)型斷言,這樣可以避免反射帶來(lái)的性能損耗。文中提到的幾種檢測(cè)方式的代碼語(yǔ)法都比較新 (nan) 奇 (kan) ,讀者可以參考代碼的注釋部分幫助理解。

聲明:本文內(nèi)容及配圖由入駐作者撰寫(xiě)或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場(chǎng)。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問(wèn)題,請(qǐng)聯(lián)系本站處理。 舉報(bào)投訴
  • VaR
    VaR
    +關(guān)注

    關(guān)注

    0

    文章

    39

    瀏覽量

    11504
  • API接口
    +關(guān)注

    關(guān)注

    1

    文章

    85

    瀏覽量

    10731
  • go語(yǔ)言
    +關(guān)注

    關(guān)注

    1

    文章

    158

    瀏覽量

    9243
收藏 人收藏

    評(píng)論

    相關(guān)推薦

    HarmonyOS Next原生應(yīng)用開(kāi)發(fā)-從TS到ArkTS的適配規(guī)則(十)

    implements 規(guī)則:arkts-implements-only-iface 級(jí)別:錯(cuò)誤 ArkTS不允許類(lèi)被implements,只有接口可以被implements。 Type
    發(fā)表于 07-29 16:02

    150 面向?qū)ο蠼涌?實(shí)現(xiàn)implements #硬聲創(chuàng)作季

    編程程序代碼
    充八萬(wàn)
    發(fā)布于 :2023年07月26日 02:36:18

    在三相電能測(cè)量系統(tǒng)實(shí)現(xiàn)電能質(zhì)量分析的參考設(shè)計(jì)包括BOM及層圖

    描述The TIDM-THDREADING reference design implements power quality analysis in a three-phase energy
    發(fā)表于 09-10 09:02

    基于LUT的輸入處理的FPGA實(shí)現(xiàn)-應(yīng)用筆記

    table (LUT). It implements a piecewise first-order linear approximation of a nonlinear function.
    發(fā)表于 09-14 21:32

    160MHz帶寬標(biāo)準(zhǔn)無(wú)線信號(hào)測(cè)試儀的IF子系統(tǒng)包括BOM及層圖

    描述This reference design implements an IF subsystem for a standard wireless signal tester
    發(fā)表于 09-18 09:05

    電壓三倍器實(shí)現(xiàn)高輸入至輸出升壓比的轉(zhuǎn)換器參考設(shè)計(jì)

    描述This boost converter implements a voltage tripler which allows a high input-to-output boost
    發(fā)表于 09-19 09:14

    簡(jiǎn)易6LoWPAN網(wǎng)狀終端節(jié)點(diǎn)參考設(shè)計(jì)包括BOM及層圖

    描述This reference design implements a simple RF mesh network end node for smart meter Advanced
    發(fā)表于 10-26 10:07

    實(shí)現(xiàn)兩個(gè)小尺寸集成FET的8V-20V輸入同步降壓轉(zhuǎn)換器

    描述The PMP11225 reference design implements two small-footprint integrated FET synchronous buck
    發(fā)表于 12-06 11:51

    dspic30f5011陷入未知狀態(tài)

    嗨,AllI有一個(gè)非常困難的問(wèn)題:(經(jīng)過(guò)幾天的正常工作,DSPIC30F5011卡在一個(gè)未知的狀態(tài)。只有重置可以釋放它。兩個(gè)提示:1。SW實(shí)現(xiàn)16秒看門(mén)狗,在這個(gè)問(wèn)題STATE2中似乎沒(méi)有激活。SW
    發(fā)表于 05-07 12:26

    Lock體系結(jié)構(gòu)和讀寫(xiě)鎖機(jī)制解析

    接口之一,規(guī)定了資源鎖使用的幾個(gè)基礎(chǔ)方法。ReentrantLock類(lèi)實(shí)現(xiàn)Lock接口的可重入鎖,即線程如果獲得當(dāng)前實(shí)例的鎖,并進(jìn)入任務(wù)方法,在線程沒(méi)有釋放鎖的狀態(tài)下,可以再次進(jìn)入任務(wù)方法,特點(diǎn):互斥
    發(fā)表于 01-05 17:53

    #HarmonyOS征文#—HarmonyOS實(shí)現(xiàn)雙擊事件

    1. 雙擊事件雙擊事件和單擊事件有些類(lèi)似,也有四種實(shí)現(xiàn)的方法1.通過(guò)id找到組件。 2.給按鈕組件設(shè)置雙擊事件。 3.本類(lèi)實(shí)現(xiàn)DoubleClickedListener接口重寫(xiě)。 4.重寫(xiě)
    發(fā)表于 07-28 10:49

    HarmonyOS實(shí)戰(zhàn)—實(shí)現(xiàn)長(zhǎng)按事件

    實(shí)現(xiàn)案例:長(zhǎng)按按鈕修改文本內(nèi)容新建項(xiàng)目:ListenerApplication3ability_main MainAbilitySlicepackage
    發(fā)表于 08-12 11:44

    使用AT89C2051微控制器實(shí)現(xiàn)簡(jiǎn)單溫度計(jì)的設(shè)計(jì)

    The system presented in this application note implements a simple digital thermometerthat includes
    發(fā)表于 06-27 11:34 ?75次下載

    SN65LVDS387,SN75LVDS387,SN65LV

    This family of four, eight, and sixteen differential line drivers implements the electrical
    發(fā)表于 08-26 17:42 ?15次下載

    基本組合邏輯功能雙向管腳的Verilog HDL源代碼

    電子發(fā)燒友網(wǎng)核心提示: 本例程是Verilog HDL源代碼:關(guān)于基本組合邏輯功能中雙向管腳的功能實(shí)現(xiàn)源代碼。 Verilog HDL: Bidirectional Pin This example implements a clocked bidirectional p
    發(fā)表于 10-15 11:28 ?1694次閱讀