【问题标题】:mapstructure json into a structure with nested dictionary将 json 映射到具有嵌套字典的结构中
【发布时间】:2023-01-11 12:14:51
【问题描述】:

我是戈朗的新手。我有一个 json 文件,其中包含我想要解析和填充的嵌套结构。

我正在尝试使用 mapstructure 来尝试填充。我能够为简单的结构做到这一点。但是当涉及到字典数组(键:结构)时。 map[string]interface{} 似乎因 runtime error: index out of range 而失败。

我尝试对下面的 json 示例执行以下操作。

type Window struct {
    loc    []int
    wrtc   string
    label  string
}

type View struct {
    windows   []Window
}

type Views struct {
    views []View
}

type Desktop struct {
    views                 []Views  `mapstructure:views`
    rotation_speed        string   `mapstructure:"rotationSpeed" json:rotationSpeed"`
}

func main() {
        file, _ := ioutil.ReadFile("test.json")

        data := Desktop{}

        _ = json.Unmarshal([]byte(file), &data)

        fmt.Println("data: ", data.views[0])
}

{
"desktop": {
    "view": [{// configs for view1
                 "random_id1": {
                         "loc": [0,0,640,360],
                         "wrtc": "some string",
                         "label": "window 1"
                 },
                 "random_id213443": {
                         "loc": [640,360,1280,720],
                         "wrtc": "some string blah",
                         "label": "window 2"
                 },
                 // more windows with random ids....
              },
              {
               // configs for view2...
              }
             ],
    "rotationSpeed": 30
}

由于窗口 id 是随机的,我无法在结构中定义它。 我尝试使用mapstructure:",squash",但似乎也失败了。

感谢您对此提供的任何帮助。

【问题讨论】:

  • 你不需要地图结构。 JSON 解组可以解决这个问题。您需要导出您的结构成员(将它们大写)。 view 元素是一个[]map[string]View,其中 View 是每个视图的结构。
  • 您也可以通过更改建模来避免(而不是解决)此问题,而不是键中的随机 ID,它们可以在值中,因此从映射更改为数组。
  • 这回答了你的问题了吗? JSON and dealing with unexported fields
  • @BurakSerdar 非常感谢您的回复。我导出了struct的成员,把View成员改成了View Structure的map。现在它没有段错误,但似乎 View 数组中没有任何内容(所以基本上它没有填充它。我还尝试更改 json 结构以使 random_id 成为 @Cadmium 建议的结构的一部分,但我无法得到它解析。
  • 发布更新的代码,我们可以尝试找出

标签: go


【解决方案1】:

@Burak Serdar 是对的

你不需要地图结构。 JSON 解组可以解决这个问题。

你的代码有很多错误,比如结构、大写、“视图”等。

下面是一个演示:

package main

import (
    "encoding/json"
    "fmt"
)

var data = `
{
    "desktop":{
        "view":[
            {
                "random_id1_1":{
                    "loc":[
                        0,
                        0,
                        640,
                        360
                    ],
                    "wrtc":"some string",
                    "label":"window 1"
                },
                "random_id1_2":{
                    "loc":[
                        640,
                        360,
                        1280,
                        720
                    ],
                    "wrtc":"some string blah",
                    "label":"window 2"
                }
            },
            {
                "random_id2_1":{
                    "loc":[
                        0,
                        0,
                        640,
                        360
                    ],
                    "wrtc":"some string",
                    "label":"window 1"
                },
                "random_id2_2":{
                    "loc":[
                        640,
                        360,
                        1280,
                        720
                    ],
                    "wrtc":"some string blah",
                    "label":"window 2"
                }
            }
        ],
        "rotationSpeed":30
    }
}
`

type Window struct {
    Loc   []int
    Wrtc  string
    Label string
}

type Desktop struct {
    View           []map[string]Window
    Rotation_speed int `json:"rotationSpeed" mapstructure:"rotationSpeed"`
}

type Config struct {
    Desktop Desktop
}

func main() {
    c := Config{}
    json.Unmarshal([]byte(data), &c)
    fmt.Println("json.Unmarshal: ", c)
}
json.Unmarshal:  {{[map[random_id1_1:{[0 0 640 360] some string window 1} random_id1_2:{[640 360 1280 720] some s
tring blah window 2}] map[random_id2_1:{[0 0 640 360] some string window 1} random_id2_2:{[640 360 1280 720] some
 string blah window 2}]] 30}}

如果你想要Viewstruct,你也可以通过“remain”使用mapstructure

type Window struct {
    Loc   []int
    Wrtc  string
    Label string
}

type View struct {
    Windows map[string]Window `mapstructure:",remain"`
}

type Desktop struct {
    View           []View
    Rotation_speed int `json:"rotationSpeed" mapstructure:"rotationSpeed"`
}

type Config struct {
    Desktop Desktop
}

func main() {
    c2 := Config{}
    m := map[string]interface{}{}
    _ = json.Unmarshal([]byte(data), &m)
    mapstructure.Decode(m, &c2)
    fmt.Println("mapstructure: ", c2)
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-08-03
    • 2021-07-06
    • 1970-01-01
    • 2020-03-23
    • 1970-01-01
    • 1970-01-01
    • 2020-09-01
    • 1970-01-01
    相关资源
    最近更新 更多