2016-01-20 67 views
1

很簡單的例子,我想:多態性Golang

我從結構A(普通功能)B和使用功能第一步的對象。我需要重新定義B中運行的函數step2。

package main 

import "fmt" 

type A struct {} 

func (a *A) step1() { 
    a.step2(); 
} 

func (a *A) step2() { 
    fmt.Println("get A"); 
} 


type B struct { 
    A 
} 

func (b *B) step2() { 
    fmt.Println("get B"); 
} 

func main() { 
    obj := B{} 
    obj.step1() 
} 

我該怎麼辦?

// maybe 
func step1(a *A) { 
    self.step2(a); 
} 
+0

您必須重新考慮模型,因爲重寫方法根本不適用於Go的OOP構造。就像如果你在A中嵌入A然後調用在A和B上定義的方法C,哪個版本被調用甚至沒有定義;規範中沒有方法解析規則。不要試圖去做。無論你想要完成什麼,都可以通過對象之間略微不同的關係來有效地完成。 – evanmcdonnal

+2

@evanmcdonnal:它不是未定義的,它被定義爲不明確。如果存在衝突的嵌入式標識符,則會出現編譯時錯誤,指出「模糊選擇器」。 – JimB

+3

@Harlam:你不能像繼承一樣構造類型。嵌入類型不能調用外部類型(並且對此不瞭解),因爲嵌入只不過是自動委派。 A中沒有B的'step2',只有'B.A.step1()'的簡寫版本。 – JimB

回答

6

Go不做多態性。你必須重新做你想做的接口和函數(而不是方法),接受這些接口。

因此,想一下每個對象需要滿足哪個接口,然後在該接口上需要哪些功能。在標準庫中有很多很好的例子,例如io.Reader,io.Writer以及那些工作的功能,例如io.Copy

Here is my attempt將您的示例改寫爲該樣式。它沒有什麼意義,但希望它會給你一些工作。

package main 

import "fmt" 

type A struct { 
} 

type steps interface { 
    step1() 
    step2() 
} 

func (a *A) step1() { 
    fmt.Println("step1 A") 
} 

func (a *A) step2() { 
    fmt.Println("get A") 
} 

type B struct { 
    A 
} 

func (b *B) step2() { 
    fmt.Println("get B") 
} 

func step1(f steps) { 
    f.step1() 
    f.step2() 
} 

func main() { 
    obj := B{} 
    step1(&obj) 
}