go語言既不支援類和對象,也不支援繼承。但是go提供了結構和方法。。
golang中沒有繼承的概念,但是可以使用組合結構和方法來實作類似c++等進階的繼承
#include <iostream>
using namespace std;
class Person {
public:
void Say();
};
void Person::Say() {
cout << "I'm a person." << endl;
}
// 繼承
class Student : public Person {
};
int main() {
Student s;
s.Say();
return 0;
}
golang實作類似功能
package main
type Person struct {
}
func (p *Person) Say() {
println("I'm a person.")
}
// 組合
type Student struct {
Person
}
func main() {
var s Student
s.Say()
}
這兩個程式運作之後結果都是:
I'm a person.
Go可以通過組合另一個類型來"繼承"它的所有行為,十分直覺。。。
但是c++和go的這2段代碼表達的意義還是有差别的:
c++類繼承表示Person類是Student類的父類,具有一種層次關系
Go的組合則表示Student 是個Person,是以Student包含了Person的所有行為,Person能幹的事兒,Student肯定也能幹,Student骨子裡還是一個Person。。。
例子2:
package main
import "fmt"
type Base struct {
Name string
}
func (b *Base) SetName(name string) {
b.Name = name
}
func (b *Base) GetName() string {
return b.Name
}
// 組合,實作繼承
type Child struct {
base Base // 這裡儲存的是Base類型
}
// 重寫GetName方法
func (c *Child) GetName() string {
c.base.SetName("modify...")
return c.base.GetName()
}
// 實作繼承,但需要外部提供一個Base的執行個體
type Child2 struct {
base *Base // 這裡是指針
}
func (c *Child2) GetName() string {
c.base.SetName("canuser?")
return c.base.GetName()
}
func main() {
c := new(Child)
c.base.SetName("world")
fmt.Println(c.GetName())
c2 := new(Child2)
c2.base = new(Base) // 因為Child2裡面的Base是指針類型,是以必須提供一個Base的執行個體
fmt.Println(c2.GetName())
}