Go Struct JSON 数组数组
Posted
技术标签:
【中文标题】Go Struct JSON 数组数组【英文标题】:Go Struct JSON array of arrays 【发布时间】:2021-10-08 21:48:18 【问题描述】:我在尝试从特定请求响应映射一些数据时遇到问题,因为在 seriesLabels 内部:有数据没有属性名称 (int,string),所以我很困惑如何映射该数据:
这是服务响应:
"data":
"seriesLabels": [
[
0,
"(none)"
],
[
0,
"Cerveza"
],
[
0,
"Cigarros"
],
[
0,
"Tecate"
],
[
0,
"Cafe"
],
[
0,
"Amstel"
],
[
0,
"Leche"
],
[
0,
"Ultra"
],
[
0,
"Coca cola"
],
[
0,
"Agua"
]
]
我映射该信息的结构是:
type PopularWord struct
Data *Data `json:"data"`
type Data struct
SeriesLabels []*SeriesLabels `json:"seriesLabels"`
type SeriesLabels struct
value int32 `json:""`
name string `json:""`
我做错了什么?声明结构的正确方法是什么?
【问题讨论】:
你可以看看这个(非常)有用的网站mholt.github.io/json-to-go 【参考方案1】:seriesLabels
是一个JSON数组,它的元素也是JSON数组。
要解析一个 JSON 数组,你可以在 Go 中使用切片:
type Data struct
SeriesLabels [][]interface
测试它:
var pw *PopularWord
if err := json.Unmarshal([]byte(src), &pw); err != nil
panic(err)
fmt.Println(pw)
for _, sl := range pw.Data.SeriesLabels
fmt.Println(sl)
输出(在Go Playground 上试试):
&0xc000120108
[0 (none)]
[0 Cerveza]
[0 Cigarros]
[0 Tecate]
[0 Cafe]
[0 Amstel]
[0 Leche]
[0 Ultra]
[0 Coca cola]
[0 Agua]
要将内部数组作为结构值,您可以实现自定义解组:
type Data struct
SeriesLabels []*SeriesLabels `json:"seriesLabels"`
type SeriesLabels struct
value int32
name string
func (sl *SeriesLabels) UnmarshalJSON(p []byte) error
var s []interface
if err := json.Unmarshal(p, &s); err != nil
return err
if len(s) > 0
if f, ok := s[0].(float64); ok
sl.value = int32(f)
if len(s) > 1
if s, ok := s[1].(string); ok
sl.name = s
return nil
测试代码一样,输出(在Go Playground上试试这个):
&0xc0000aa0f0
&0 (none)
&0 Cerveza
&0 Cigarros
&0 Tecate
&0 Cafe
&0 Amstel
&0 Leche
&0 Ultra
&0 Coca cola
&0 Agua
【讨论】:
【参考方案2】:问题是SeriesLabels
在 JSON 中表示为一个数组。如果你想使用encoding/json
,你必须实现Unmarshaler接口来解码它(否则它只会接受JSON对象)。
还好代码很简单:
func (s *SeriesLabels) UnmarshalJSON(d []byte) error
arr := []interface&s.value, &s.name
return json.Unmarshal(d, &arr)
请注意,此代码会忽略无效输入(数组太长或类型不正确)。根据您的需要,您可能希望在调用 json.Unmarshal
之后添加检查数组长度和内容(指针)没有改变。
还有其他用于 Go 的 JSON 解析库使这变得不那么麻烦,例如 gojay。
【讨论】:
以上是关于Go Struct JSON 数组数组的主要内容,如果未能解决你的问题,请参考以下文章