亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

如何使用相同的方法簽名實現兩個不同的接口

如何使用相同的方法簽名實現兩個不同的接口

Go
LEATH 2021-09-13 10:35:39
假設我必須實現在兩個不同的包中聲明的兩個不同的接口(在兩個不同的獨立項目中)。我在包裹里 Apackage Atype interface Doer {    Do() string}func FuncA(Doer doer) {     // Do some logic here using doer.Do() result     // The Doer interface that doer should implement,      // is the A.Doer}并在包 Bpackage Btype interface Doer {    Do() string}function FuncB(Doer doer) {    // some logic using doer.Do() result     // The Doer interface that doer should implement,      // is the B.Doer}在我的main包裹里package mainimport (    "path/to/A"    "path/to/B")type C int// this method implement both A.Doer and B.Doer but// the implementation of Do here is the one required by A !func (c C) Do() string {    return "C now Imppement both A and B"}func main() {    c := C(0)    A.FuncA(c)    B.FuncB(c) // the logic implemented by C.Do method will causes a bug here !}如何處理這種情況?
查看完整描述

2 回答

?
慕妹3146593

TA貢獻1820條經驗 獲得超9個贊

正如常見問題中提到的

使用其他語言的經驗告訴我們,擁有多種名稱相同但簽名不同的方法有時很有用,但在實踐中也可能會令人困惑和脆弱。
僅按名稱匹配并要求類型一致是 Go 類型系統中的一個主要簡化決策。

在您的情況下,您會滿足兩個接口。

您可以通過執行以下操作來測試對象(接口類型)是否滿足另一種接口類型A.Doer

if _, ok := obj.(A.Doer); ok {
}

OP補充說:

但是Do方法中實現的邏輯來滿足AB.

然后你需要在你的對象周圍實現一個包裝器:

  • DoerA,它將您的對象C作為一個字段,并A.Do()以滿足A.Do()應該如何工作的方式實現

  • DoerB,它具有與C字段相同的對象,并B.Do()以滿足B.Do()應該如何工作的方式實現

這樣,您將知道將哪個 Doer 傳遞給期望 anA.Doer或 a的函數B.Doer。
您不必Do()在原始 object 上實現一個方法C,這將無法處理A.Do()and的不同邏輯B.Do()。


查看完整回答
反對 回復 2021-09-13
?
一只甜甜圈

TA貢獻1836條經驗 獲得超5個贊

根據定義,您同時滿足以下兩點

Go 類型通過實現該接口的方法來滿足該接口,僅此而已。此屬性允許在無需修改現有代碼的情況下定義和使用接口。它支持一種促進關注點分離和改進代碼重用的結構類型,并使構建隨著代碼開發而出現的模式變得更加容易。接口的語義是 Go 具有敏捷、輕量級感覺的主要原因之一。

因此,考慮到這一點,您可以:

a) 向定義您對邏輯的期望的接口方法添加注釋(請參閱 io.Reader 接口或一個很好的示例)

b) 在接口上添加一個名為ImplementsDoerA 和ImplementsDoerB 的額外方法(也在FAQ 中提到)。


查看完整回答
反對 回復 2021-09-13
  • 2 回答
  • 0 關注
  • 270 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號