3 回答

TA贡献1891条经验 获得超3个赞
我明白你想做什么,但这是不可能的:你的Cat和Dog类型没有实现Pet接口,因为它们的Play方法采用不同的类型,所以你不能只用Play你的SuperToy.
要解决此问题,您需要创建一个Toy接口,该接口同时具有Roll和Rattle方法以及 make Pet.Play,Cat.Play并将Dog.Play此接口作为参数。
package main
type Cat struct {
}
func (cat *Cat) Play(catToy Toy) {
println("The cat is playing!", catToy.Rattle())
}
type Dog struct {
}
func (dog *Dog) Play(dogToy Toy) {
println("The dog is playing!", dogToy.Roll())
}
type Toy interface {
Roll() string
Rattle() string
}
type SuperToy struct {
}
func (toy *SuperToy) Rattle() string {
return "Rattle!!!"
}
func (toy *SuperToy) Roll() string {
return "Rolling..."
}
type Pet interface {
Play(toy Toy)
}
func main() {
cat := &Cat{}
dog := &Dog{}
superToy := &SuperToy{}
// Working
cat.Play(superToy)
dog.Play(superToy)
// Not Working
pets := []Pet{cat, dog}
for _, pet := range pets {
pet.Play(superToy)
}
}
给出输出
The cat is playing! Rattle!!!
The dog is playing! Rolling...
The cat is playing! Rattle!!!
The dog is playing! Rolling...

TA贡献1851条经验 获得超3个赞
您可以让 Play 方法接受一个interface{},然后在方法内进行类型断言:
func (dog *Dog) Play(toy interface{}) {
dogToy, isDogToy := toy.(DogToy)
if !isDogToy {
println("The dog does not know what to do with this toy!")
return
}
println("The dog is playing!", dogToy.Roll())
}
Go Playground 上的完整可执行示例:
https://play.golang.org/p/LZZ-HqpzR-Z

TA贡献1802条经验 获得超5个赞
这是另一个可行的解决方案:
package main
type CatToy interface {
Rattle() string
}
type Cat struct {
Toy CatToy
}
func (cat *Cat) Play() {
println("The cat is playing!", cat.Toy.Rattle())
}
type DogToy interface {
Roll() string
}
type Dog struct {
Toy DogToy
}
func (dog *Dog) Play() {
println("The dog is playing!", dog.Toy.Roll())
}
type SuperToy struct {
}
func (toy *SuperToy) Rattle() string {
return "Rattle!!!"
}
func (toy *SuperToy) Roll() string {
return "Rolling..."
}
type Pet interface {
Play()
}
func main() {
superToy := &SuperToy{}
cat := &Cat{superToy}
dog := &Dog{superToy}
// Working
cat.Play()
dog.Play()
// Working also
pets := []Pet{cat, dog}
for _, pet := range pets {
pet.Play()
}
}
该解决方案使Cat + CatToy和Dog + DogToy独立于main + SuperToy. 这允许提取以分离包。
- 3 回答
- 0 关注
- 95 浏览
添加回答
举报