假设我必须实现在两个不同的包中声明的两个不同的接口(在两个不同的分离项目中).
我有包裹 A
package A
type 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
}
Run Code Online (Sandbox Code Playgroud)
并在包中 B
package B
type 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
}
Run Code Online (Sandbox Code Playgroud)
在我的main包裹中
package main
import (
"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 !
}
Run Code Online (Sandbox Code Playgroud)
如何应对这种情况?
使用其他语言的经验告诉我们,使用具有相同名称但签名不同的各种方法偶尔会有用,但在实践中它也可能令人困惑和脆弱.
仅根据名称进行匹配并要求在类型中保持一致性是Go类型系统中的主要简化决策.
在您的情况下,您将满足两个接口.
您可以通过执行以下操作来测试对象(接口类型)是否满足另一种接口类型A.Doer:
if _, ok := obj.(A.Doer); ok {
}
Run Code Online (Sandbox Code Playgroud)
OP增加:
但是
Do要满足的方法中实现的逻辑与中的A完全不同B.
然后你需要在你的对象周围实现一个包装器:
DoerA,将您的对象C作为字段,并A.Do()以满足A.Do()应该如何工作的方式实现DoerB,具有与C字段相同的对象,并B.Do()以满足B.Do()应该如何工作的方式实现这样,您将知道哪个Doer传递给期望a A.Doer或a 的函数B.Doer.
你不会实现Do()你的原始对象上的方法C,这将是无法应付的不同的逻辑A.Do()和B.Do().
| 归档时间: |
|
| 查看次数: |
2747 次 |
| 最近记录: |