英文:
How to access underlying struct field value if via interface field type in Golang?
问题
通过接口直接获取结构字段值是不可能的,但是有一些技巧可以实现。
在文件"./animals/mammal.go"中,你定义了一个接口"Mammal":
type Mammal interface {
Sound()
}
在同一个文件中,你实现了一个结构体"Dog":
type Dog struct {
Name string
Age int
}
func (d *Dog) Sound() {
fmt.Println("Say my name...", d.Name)
}
在另一个包"../../police/animals.go"中,你有另一个结构体"Policeman":
type Policeman struct {
Animal Mammal
Policeman Name
ID int
}
你希望能够像这样实现它:
func (p *Policeman) Arrest() {
fmt.Println("Hands up, police! Bite him, ", p.Animal.Name)
}
但是编译器不允许这样做,因为"p.Animal"是一个接口类型。
然而,有一种应用设计技巧/模式可以实现你的需求。我的观点是,一旦我写了"Policeman"结构体,我希望确保当我将动物从狗改为猫或其他动物时,我不需要重写"Arrest"方法。这就是问题的关键所在!
英文:
Is there some trick (it is impossible directly) on how to get struct field values via interface?
I have an interface in a file ./animals/mammal.go:
type Mammal interface {
Sound()
}
I have implementation in the same file:
type Dog struct {
Name string
Age int
}
func (d *Dog) Sound {
fmt.Println("Say my name...", d.Name)
}
In other package ../../police/animals.go I have another struct:
type Policeman struct {
Animal Mammal
Policeman Name
ID int
}
And I wish to be able to implement it like this:
func (p *Policeman) Arrest {
fmt.Println("Hands up, police! Bite him, ", p.Animal.Name)
}
And compiler won't let me do that, because p.Animal is an interface type, of course...
However, is there an application design trick/pattern, that could allow me to do that. My point is, that once I wrote Policeman struct, I wish to be sure, that WHEN I CHANGE an animal from Dog to Cat or somebody else, I won't rewrite the "Arrest" method, so that's the point of the question!
答案1
得分: 1
如果在你的上下文中,以下陈述是真实的:“所有哺乳动物都有一个名字”,你可以在接口Mammal
中添加一个方法Name()
,你的示例将像这样工作:
type Mammal interface {
Sound()
Name() string
}
func (p *Policeman) Arrest {
fmt.Println("Hands up, police! Bite him, ", p.Animal.Name())
}
如果这个陈述不是真实的,那么你想要的是不可能的,因为对于没有名字的哺乳动物调用Name()
方法的处理方式仍然不清楚。
请注意,你还需要为Dog
实现Name()
方法。
英文:
If, in your context, the following statement is true "All mammals have a name", you can add a method Name()
to the interface Mammal
and your example would work like this:
type Mammal interface {
Sound()
Name() string
}
func (p *Policeman) Arrest {
fmt.Println("Hands up, police! Bite him, ", p.Animal.Name())
}
If the statement is not true, then want you want is impossible because it remains unclear what to do with a call to Name()
for a mammal that does not have a name.
Note that you then also need to implement the Name()
method for Dog
.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论