英文:
Getting invalid operation: mymap["title"] (type interface {} does not support indexing) when trying to index a map
问题
我有一个存储在map中的数据,并且我想通过键索引到map中获取值。
mdi, err := page.Metadata()
fmt.Println(mdi["title"])
然而,我一直收到错误消息invalid operation: mdi["title"] (type interface {} does not support indexing)
。我感到困惑,因为数据是一个map,我应该能够通过索引来获取值。为了确保类型清楚,我还尝试将值转换为字符串:
title, ok := mdi["title"].(string)
checkOk(ok)
fmt.Println(title)
然而,我得到了相同的错误消息。我做错了什么?
英文:
I have data that's in a map, and I want to index into the map by key to get a value.
mdi, err := page.Metadata()
fmt.Println(mdi["title"])
However I keep getting the error message invalid operation: mdi["title"] (type interface {} does not support indexing)
. I am confused, because the data is a map and I should be able to index into it to get the value. In case the type wasn't clear, I also tried to cast the value to a string:
title, ok := mdi["title"].(string)
checkOk(ok)
fmt.Println(title)
However, I got the same error message. What am I doing wrong?
答案1
得分: 100
这里的数据类型是关键。mdi
实际上不是一个映射,而是一个interface{}
,它可以是任何类型 - 映射、字符串、整数。你需要首先将其断言为具有预期键/值类型的映射,或者按照JSON和Go中概述的笨拙的case
开关进行操作。
mdi, err := page.Metadata()
md, ok := mdi.(map[string]interface{})
fmt.Println(md["title"])
英文:
The data type here was the key. mdi
was not actually a map, but an interface{}
, which could be anything - a map, a string, an int. You need to assert it to a map with expected key/value types first, or do the awkward case
switch outlined in JSON and Go.
mdi, err := page.Metadata()
md, ok := mdi.(map[string]interface{})
fmt.Println(md["title"])
答案2
得分: 0
我不确定你是否能控制page.Metadata
的行为,但如果可以的话,这种情况下有更好的方法。假设你的代码如下所示:
package main
import (
"encoding/json"
"log"
)
func Metadata() (interface{}, error) {
y := []byte(`{"metadata": {"title": "Stack Overflow"}}`)
var m map[string]interface{}
e := json.Unmarshal(y, &m)
if e != nil {
return nil, e
}
return m["metadata"], nil
}
func main() {
m, e := Metadata()
if e != nil {
log.Fatal(e)
}
s := m["title"]
println(s == "Stack Overflow")
}
你会得到与你之前遇到的相同错误。但你可以将其改为以下形式:
type Map map[string]interface{}
func (m Map) M(s string) Map {
return m[s].(map[string]interface{})
}
func (m Map) S(s string) string {
return m[s].(string)
}
func Metadata() (Map, error) {
y := []byte(`{"metadata": {"title": "Stack Overflow"}}`)
var m Map
e := json.Unmarshal(y, &m)
if e != nil {
return nil, e
}
return m.M("metadata"), nil
}
func main() {
m, e := Metadata()
if e != nil {
log.Fatal(e)
}
s := m.S("title")
println(s == "Stack Overflow")
}
然后,每当你需要索引时,只需根据你想要返回的内容调用相应的方法。如果需要返回[]interface{}
类型的切片,你也可以添加Slice
方法,并根据需要添加其他方法,例如返回整数。最后,如果你想检查Map
是否包含某个键,可以这样做:
if m["title"] != nil {
s := m.S("title")
println(s == "Stack Overflow")
}
英文:
I'm not sure if you have control over what page.Metadata
does, but if you do, a better way is available for this situation. Say your code looks like this:
package main
import (
"encoding/json"
"log"
)
func Metadata() (interface{}, error) {
y := []byte(`{"metadata": {"title": "Stack Overflow"}}`)
var m map[string]interface{}
e := json.Unmarshal(y, &m)
if e != nil {
return nil, e
}
return m["metadata"], nil
}
func main() {
m, e := Metadata()
if e != nil {
log.Fatal(e)
}
s := m["title"]
println(s == "Stack Overflow")
}
You'd get the same error you got. But you can change it to this:
type Map map[string]interface{}
func (m Map) M(s string) Map {
return m展开收缩.(map[string]interface{})
}
func (m Map) S(s string) string {
return m展开收缩.(string)
}
func Metadata() (Map, error) {
y := []byte(`{"metadata": {"title": "Stack Overflow"}}`)
var m Map
e := json.Unmarshal(y, &m)
if e != nil {
return nil, e
}
return m.M("metadata"), nil
}
func main() {
m, e := Metadata()
if e != nil {
log.Fatal(e)
}
s := m.S("title")
println(s == "Stack Overflow")
}
Then whenever you need to index, you just call the appropriate method depending on what you are wanting to return. You can also add Slice if need be []interface{}
, and further methods from what I put, for example if you need to return integer. Finally, if you want to check if Map contains key, you can do this:
if m["title"] != nil {
s := m.S("title")
println(s == "Stack Overflow")
}
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论