Golang继承指针与非指针的一个疑问
上述 结构 Persion 中 一个指针 Animal 和一个非指针的 Animal 两个有啥区别,分别应用在什么样的场合?
如果用于继承 指针的Animal 似乎就不正确了
Answers
题主,或许是你想太多了,指针嘛,就是一个传值还是传引用的区别,例如:
package main
import (
"fmt"
)
type Animal struct {
Name string
}
type Persion struct {
Animal
}
type Ppersion struct {
*Animal
}
func main() {
animal := Animal{Name: "Cat"}
persion := Persion{animal}
ppersion := Ppersion{&animal}
fmt.Println("Animal:" + animal.Name)
fmt.Println("Persion:" + persion.Name)
fmt.Println("PPersion:" + ppersion.Name)
animal.Name = "Dog"
fmt.Println("------------我是卖萌分割线------------")
fmt.Println("Animal:" + animal.Name)
fmt.Println("Persion:" + persion.Name)
fmt.Println(persion.Animal == animal)
fmt.Println("PPersion:" + ppersion.Name)
fmt.Println(ppersion.Animal == &animal)
}
你可以看到如下输出
Animal:Cat
Persion:Cat
PPersion:Cat
------------我是卖萌分割线------------
Animal:Dog
Persion:Cat
false
PPersion:Dog
true
传值和传引用,显而易见,非指针匿名字段是原结构体的一个拷贝,不影响原结构体
这会带来很多问题,所有平时见到的,指针匿名字段多一些,当然有些场景下确实需要值传递。
关于对原结构体方法的引用,至少我没有发现有太大得区别,也许如楼上说的那样,也许是我想少了
Go 语言里面只有类型嵌入,没有类型继承,请题主要以Java等OOP语言的方式去思考Go的问题,在Go里面,第一等类型是函数类型…… 你这里所说的是嵌入类型:
结构体类型可以包含匿名或者嵌入字段。也叫做嵌入一个类型。当我们嵌入一个类型到结构体中时,该类型的名字充当了嵌入字段的字段名。
package main
import (
"fmt"
)
type User struct {
Name string
Gender string
}
func (user *User) Login() {
fmt.Println("Login to the system")
}
type Manager struct {
User
Position string
}
func main() {
manager := Manager{
User: User{
Name: "某某某",
Gender: "男",
},
Position: "超级管理员",
}
manager.Login()
}
上面代码中,我们定义了一个新类型
Manager
然后把
User
类型嵌入进去,注意这个不叫继承而叫组合。
User
类型跟
Manager
类型没有关系。
当我们嵌入一个类型,这个类型的方法就变成了外部类型的方法,但是当它被调用时,方法的接受者是内部类型(嵌入类型),而非外部类型。— Effective Go
因此嵌入类型的名字充当着字段名,同时嵌入类型作为内部类型存在,我们可以使用下面的调用方法:
manager.User.Login()
这儿我们通过类型名称来访问内部类型的字段和方法。然而,这些字段和方法也同样被提升到了外部类型:
manager.Login()
下面是 Go 语言中内部类型方法集提升的规则:
给定一个结构体类型 S 和一个命名为 T 的类型,方法提升像下面规定的这样被包含在结构体方法集中:
- 如果 S 包含一个匿名字段 T,S 和 *S 的方法集都包含接受者为 T 的方法提升。
- 对于 *S 类型的方法集包含接受者为 *T 的方法提升
- 如果 S 包含一个匿名字段 *T,S 和 *S 的方法集都包含接受者为 T 或者 *T 的方法提升