dongzhuo1958 2018-12-07 01:00
浏览 38
已采纳

具体类型与返回类型上的接口不匹配

I am playing around with Go and found a problem I can't get around. Suppose I have my code like this:

// Imagine this is an external package for querying MySQL: I run a query 
// and it gives me back a struct with a method "Result" to get the result
// as a string
// I can NOT modify this code, since it is an external package
package bar

type MySQL struct {}

func (m *MySQL) RunQuery() *MySQLResult {
    return &MySQLResult{}
}

type MySQLResult struct {}

func (r *MySQLResult) Result() string {
    return "foo"
}

I imported the package and started to use it:

// I created a little runner to help me
func run(m *bar.MySQL) string {
    return m.RunQuery().Result()
}

func main() {
    m := &bar.MySQL{}
    fmt.Println(run(m)) // Prints "foo"
}

I really like my helper "run", but I'd like to make it more generous: I don't expect people to always pass me a MySQL client. It could be anything that has a "RunQuery" and "Result" method. So I try to use interfaces:

type AnyDB interface {
    RunQuery() interface{ Result() string }
}

func run(m AnyDB) string {
    return m.RunQuery().Result()
}

Sadly, this doesn't compile anymore. I get this error:

cannot use m (type *MySQL) as type AnyDB in argument to run:
    *MySQL does not implement AnyDB (wrong type for RunQuery method)
        have RunQuery() *MySQLResult
        want RunQuery() interface { Result() string }

Is this not supported by Go, or am I doing something wrong?

  • 写回答

1条回答 默认 最新

  • duai4512 2018-12-07 01:28
    关注

    RunQuery should return interface, otherwise you always have to deal with strong type.

    AnyDB is not required, I added it for connivence.

    AnyResult should be defined in bar package or being imported into it.

    type AnyDB interface {
        RunQuery() AnyResult
    }
    
    type MySQL struct{}
    
    func (m *MySQL) RunQuery() AnyResult {
        return &MySQLResult{}
    }
    
    type AnyResult interface {
        Result() string
    }
    
    type MySQLResult struct{}
    
    func (r *MySQLResult) Result() string {
        return "foo"
    }
    
    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 装 pytorch 的时候出了好多问题,遇到这种情况怎么处理?
  • ¥20 IOS游览器某宝手机网页版自动立即购买JavaScript脚本
  • ¥15 手机接入宽带网线,如何释放宽带全部速度
  • ¥30 关于#r语言#的问题:如何对R语言中mfgarch包中构建的garch-midas模型进行样本内长期波动率预测和样本外长期波动率预测
  • ¥15 ETLCloud 处理json多层级问题
  • ¥15 matlab中使用gurobi时报错
  • ¥15 这个主板怎么能扩出一两个sata口
  • ¥15 不是,这到底错哪儿了😭
  • ¥15 2020长安杯与连接网探
  • ¥15 关于#matlab#的问题:在模糊控制器中选出线路信息,在simulink中根据线路信息生成速度时间目标曲线(初速度为20m/s,15秒后减为0的速度时间图像)我想问线路信息是什么