2 回答
TA贡献1877条经验 获得超6个赞
不,你要嵌入A在B。B没有定义Discover,因此A总是调用on 版本。该方法有一个类型的接收器,A并且A不B知道它嵌入在B. 因此A只能称其为自己的版本GetTest()。
B满足发现接口的唯一原因是它已A嵌入。它间接地实现它。如果你想打开功能B,你必须定义它B。这根本不是多态性,而是组合。B不是A,B有A。如果你想要多态,你可以使用接口并实现它们。B是一个可发现的,但只是因为它有一个A.
我认为这只是示例,但您实际上根本没有理由使用这种Discovery方法。您的界面应该只需要GetTest。不要将嵌入与继承混淆。Go 中没有继承。如果您想要多态行为,您可以通过实现接口来实现它,并且您不能像这样偷工减料,因为嵌入式类型和嵌入器之间的关系不是继承之一,没有基类或“覆盖”。
TA贡献1963条经验 获得超6个赞
为了补充@evanmcdonnal 的观点,嵌入既不是继承也不是多态。继承恰好是一种方便,您可以免费获得接口的实现,但在 Go 中,它是显式的。正如@evanmcdonnal 所指出的,嵌入可能看起来像继承,但并非如此。
相反,您应该将概念多态性与继承以及嵌入和继承分开。大多数面向对象的语言都没有进行比较。例如,下面将是多态性的实现。请注意,Discover需要一个接口,A并B实现了接口,使得函数本身多态性。
package main
import "fmt"
type A struct{}
type B struct{}
type Test interface{
GetTest() string
}
func (a *A) GetTest() string {
return "i am in A"
}
func (b *B) GetTest() string {
return "i am in B"
}
func Discover(t Test) string {
return t.GetTest()
}
func main() {
a := &A{}
b := &B{}
fmt.Println(Discover(a))
fmt.Println(Discover(b))
}
- 2 回答
- 0 关注
- 263 浏览
添加回答
举报
