json字符串转golang map
我们知道golang处理json字符串时,需要先转成struct,并且struct必须是确定的。
有时候我们传递的json是不固定的,针对每种情况都写一个struct比较麻烦,有没有处理不确定json的方法呢?
答案是有的
var a string = "{\"a\":1,\"b\":\"xx\"}"
var b map[string]interface{}
err := json.Unmarshal([]byte(a), &b)
if err != nil {
log.Println(err)
return
}
如上面的示例,a是一个json字符串,b就是用来接收json字符串的map,其key是string,value是interface。
这样反序列化就可以把json字符串映射成一个golang的map,用起来与struct一样。
判断map中key是否存在
因为json字符串是不确定的,所以我们会用到判断某个key是否在map中,其方法如下
if _, ok := b["a"]; ok {
log.Println(b["a"])
}
如果有a,ok是true;如果没有a,ok是false。
判断value类型
既然json字符串不固定,key确认是否存在了,还需要确认value的类型。
if reflect.TypeOf(b["a"]).Kind() == reflect.Float64 {
}
golang会把数字转成float64,默认按照最大的存储数字转换,避免数据丢失。reflect.TypeOf
用来获取数据类型,获取的是一个结构体,Kind
函数获取具体的类型。reflect.Float64
是系统定义的类型,常见的类型都有,包括map,string等。
value数据转换
通过b["a"]
获取的是interface,因为本身我们的map就是interface。
赋值的时候可能会遇到类型转换,比如把float64转成int,如果直接用常见的int(b["a"])
会报错
需要先用b["a"].(float64)
转成对应的数据,再进行int(b["a"].(float64))
转换。
能否用b["a"].(int)
直接转换?答案是不可以。golang对类型限制的比较严,会报错。
https://stackoverflow.com/questions/35583735/unmarshaling-into-an-interface-and-then-performing-type-assertion
https://pkg.go.dev/encoding/json#Unmarshal