英文:
Q: golang pointer to map[string]interface{}
问题
我(golang 新手)正在尝试在一个函数中创建一个 map[string]interface{}。代码可以编译和运行,但是 map 是空的。
package main
import (
"fmt"
"encoding/json"
)
func main() {
var f interface{}
var sJson string // JSON string from VT
var err error // errors
var b []byte // bytearray of JSON string
var rootMap map[string]interface{}
rootMap = make(map[string]interface{})
sJson=`{"key": "foo"}`
fmt.Println(sJson)
err = json2map(&b, &sJson, f, rootMap)
if err != nil { return }
switch v := rootMap["key"].(type) {
case float64:
fmt.Printf("Value: %d",v)
case string:
fmt.Printf("Value: %s", v)
case nil:
fmt.Println("key is nil")
default:
fmt.Println("type is unknown")
}
}
func json2map(b *[]byte, sJson *string, f interface{}, myMap map[string]interface{}) error {
var err error
*b = []byte(*sJson)
err = json.Unmarshal(*b,&f)
myMap = f.(map[string]interface{})
return err
}
输出结果为:
{"key": "foo"}
key is nil
我找到了这篇文章,其中描述了如何使用 map[string]string。这段代码按预期工作:
package main
import (
"fmt"
)
type MyType struct {
Value1 int
Value2 string
}
func main() {
myMap := make(map[string]string)
myMap["key"] = "foo"
ChangeMyMap(myMap)
fmt.Printf("Value : %s\n", myMap["key"])
}
func ChangeMyMap(TheMap map[string]string) {
TheMap["key"] = "bar"
}
所以我认为我的问题与 map 的类型为 interface 而不是 string 有关,但我无法解释为什么第一个代码不起作用,而第二个代码起作用。
英文:
I (golang newbie) am trying to create a map[string]interfaces{} in a function. The code compiles and runs but the map is empty.
package main
import (
"fmt"
"encoding/json"
)
func main() {
var f interface{}
var sJson string // JSON string from VT
var err error // errors
var b []byte // bytearray of JSON string
var rootMap map[string]interface{}
rootMap = make(map[string]interface{})
sJson=`{"key": "foo"}`
fmt.Println(sJson)
err = json2map(&b, &sJson, f, rootMap)
if err != nil { return }
switch v := rootMap["key"].(type) {
case float64:
fmt.Printf("Value: %d",v)
case string:
fmt.Printf("Value: %s", v)
case nil:
fmt.Println("key is nil")
default:
fmt.Println("type is unknown")
}
}
func json2map(b *[]byte, sJson *string, f interface{}, myMap map[string]interface{}) error {
var err error
*b = []byte(*sJson)
err = json.Unmarshal(*b,&f)
myMap = f.(map[string]interface{})
return err
}
The output is:
{"key": "foo"}
key is nil
I found this article which describes how to use map[string]string. This code works as expected:
package main
import (
"fmt"
)
type MyType struct {
Value1 int
Value2 string
}
func main() {
myMap := make(map[string]string)
myMap["key"] = "foo"
ChangeMyMap(myMap)
fmt.Printf("Value : %s\n", myMap["key"])
}
func ChangeMyMap(TheMap map[string]string) {
TheMap["key"] = "bar"
}
So I think my problem has to do with the map being of type interface instead of string but I cannot tell why the first code doesn't work, while the 2nd does.
答案1
得分: 5
这里有几个导致混淆的问题:
- 你根本不需要
b
。你正在传递一个指向字节切片的指针,在函数内部重新分配它。直接使用字符串即可。 - 没有必要使用指向
sJson
字符串的指针。字符串是不可变的,并且你并没有尝试重新分配sJson
变量。 - 你正在将空接口解组为
myMap
的内容,然后尝试重新分配myMap
变量的内容为f
的内容。由于myMap
不是指针,该赋值只在函数内部有效。直接解组为myMap
。
如果你更改这些内容,你会发现 json2map
函数最终只有一行,并且可以完全删除:
func json2map(sJson string, myMap map[string]interface{}) error {
return json.Unmarshal([]byte(sJson), &myMap)
}
英文:
There's a number of things causing confusion here:
- You don't need
b
at all. You're passing a pointer to a byte slice that you're reassigning inside the function. Just use the string directly. - There's no need to us a pointer to the
sJson
string. Strings are immutable, and you're not trying to reassign thesJson
variable. - You're unmarshaling into an empty interface, and then trying to reassign the
myMap
variable to the contents off
. SincemyMap
isn't a pointer, that assignment is only scoped to within the function. Just unmarshal directly intomyMap
If you change those things, you'll find the json2map
function ends up being one line, and can be dropped altogether:
func json2map(sJson string, myMap map[string]interface{}) error {
return json.Unmarshal([]byte(sJson), &myMap)
}
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论