错误:需要类型断言

huangapple go评论72阅读模式
英文:

ERROR: need type assertion

问题

我以为我已经断言过了(就我学习Go的程度而言),但我一直收到这个错误消息:cannot use readBack["SomePIN"] (type interface {}) as type string in argument to c.String: need type assertion

以下是我的代码(这段代码片段来自一个请求处理函数,我正在使用Echo Web框架和Tiedot NoSQL数据库):

// 要获取查询结果文档,只需按照Tiedot的readme.md中所述进行读取
for id := range queryResult {
    readBack, err := aCollection.Read(id)
    if err != nil {
        panic(err)
    }
    if readBack["OtherID"] == otherID {
        if _, ok := readBack["SomePIN"].(string); ok {
            return c.String(http.StatusOK, readBack["SomePIN"])
        }
    }
}

请注意,这是一个代码片段,可能需要根据你的实际情况进行适当的调整。

英文:

I thought I have asserted (as far as I've learnt Go), but I keep getting this error
cannot use readBack["SomePIN"] (type interface {}) as type string in argument to c.String: need type assertion

Here is my code (this snippet is from a Request Handler function and I'm using Echo Web framework and Tiedot NoSQL database)

// To get query result document, simply 
// read it [as stated in the Tiedot readme.md]
for id := range queryResult {
    readBack, err := aCollection.Read(id)
    if err != nil {
	    panic(err)
    }
    if readBack["OtherID"] == otherID {
	    if _, ok := readBack["SomePIN"].(string); ok {
		    return c.String(http.StatusOK, readBack["SomePIN"])
	    }
    }
}

答案1

得分: 6

你正在将readBack["SomePIN"]断言为字符串 - if语句中。然而,这对readBack["SomePIN"]没有任何改变 - 它仍然是一个interface{}类型。在Go语言中,类型是不会改变的。以下是可以工作的代码示例:

for id := range queryResult {
    readBack, err := aCollection.Read(id)
    if err != nil {
        panic(err)
    }
    if readBack["OtherID"] == otherID {
        if somePIN, ok := readBack["SomePIN"].(string); ok {
            return c.String(http.StatusOK, somePIN)
        }
    }
}

你之前丢弃了类型断言的字符串值,但是你需要它。所以保留它,作为somePIN,然后使用它。

最后注意一点 - 使用value, ok = interfaceVal.(type)的语法是一个好的实践。如果interfaceVal不是字符串类型,你将得到value = ""ok = false。如果你从类型断言中省略了ok值,并且interfaceVal不是字符串类型,程序将会panic。

英文:

You are asserting readBack["SomePIN"] as a string - in the if statement. That doesn't make any change to readBack["SomePIN"], however - it's still an interface{}. In Go, nothing ever changes type. Here's what will work:

for id := range queryResult {
    readBack, err := aCollection.Read(id)
    if err != nil {
        panic(err)
    }
    if readBack["OtherID"] == otherID {
        if somePIN, ok := readBack["SomePIN"].(string); ok {
            return c.String(http.StatusOK, somePIN)
        }
    }
}

You were tossing the string value from your type assertion, but you want it. So keep it, as somePIN, and then use it.

Final note - using the value, ok = interfaceVal.(type) syntax is a good practice. If interfaceVal turns out to be a non-string, you'll get value = "" and ok = false. If you eliminate the ok value from the type assertion and interfaceVal is a non-string, the program will panic.

答案2

得分: 3

看起来你正在将其转换为具体类型并丢弃转换结果,我认为这样应该可以工作:

if somePinString, ok := readBack["SomePIN"].(string); ok {
    return c.String(http.StatusOK, somePinString)
}

请注意,这是一段Go语言代码。

英文:

It looks like your converting to a concrete type and throwing away the conversion, I think this should work:

    if somePinString, ok := readBack["SomePIN"].(string); ok {
        return c.String(http.StatusOK, somePinString)
    }

huangapple
  • 本文由 发表于 2016年11月19日 02:18:32
  • 转载请务必保留本文链接:https://go.coder-hub.com/40683635.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定