【问题标题】:Decode both map and array json解码地图和数组 json
【发布时间】:2016-08-23 09:18:25
【问题描述】:

如果没有项目,外部 API 返回空数组:

{"items":[]}

...或带有项目的地图:

{"items":{"1": {...}, "2": {...}}}

如何解码它们?我尝试使用这个结构:

var response struct {
    Items map[string]Item
    Array []Item `json:"items"`
}

但它不起作用。

更新:最好(数组和对象)都生成map[string]Item(空和填充)

【问题讨论】:

  • 请注意我想要解码现有的json,我有一个键两种类型的值
  • @Amd 看问题,请看数组总是空的,应该是空的map[string]Item{}对象总是填充的,所以应该填充map[string]Item{...}
  • @Amd 它应该在one 类型的map[string]Item 字段中解码arrayobject

标签: arrays json parsing dictionary go


【解决方案1】:

如果您需要解组为变量类型,最简单的方法是解组为 map[string]interface{} 和类型断言(或在本例中为类型切换)。

func Unmarshal(data []byte) (map[string]Item, error) {
    var d struct {
        Items interface{} `json:"items"`
    }
    if err := json.Unmarshal(data, &d); err != nil {
        return nil, err
    }
    switch dv := d.Items.(type) {
    case []interface{}:
        if len(dv) == 0 {
            return nil, nil
        }
    case map[string]interface{}:
        m := make(map[string]Item)
        for k, v := range dv {
            m[k] = Item(v)
        }
        return m, nil
    }
    // fallthrough return if different type, or non-empty array
    // Could have put this in a default case, but this catches non-empty arrays too
    return nil, fmt.Errorf("unexpected type in json")
}

这是一个示例,显示它适用于您提供的两个示例:https://play.golang.org/p/c0oZX2-xpN

【讨论】:

    【解决方案2】:

    试试这个工作代码(A):

    package main
    
    import (
        "encoding/json"
        "fmt"
    )
    
    type Item int
    
    type response struct {
        Items map[string]Item `json:"Items"`
        Array []Item          `json:"Array"`
    }
    
    func main() {
        var d response
        err := json.Unmarshal([]byte(`{"Items":{"A":1,"B":2,"C":3},"Array":[]}`), &d)
        if err != nil {
            panic(err)
        }
        fmt.Println(d)
    }
    

    输出:

    {map[C:3 A:1 B:2] []}
    

    试试这个工作代码(B):

    package main
    
    import (
        "encoding/json"
        "fmt"
    )
    
    type Item int
    
    type response struct {
        Items map[string]Item `json:"Items"`
        //Array []Item          `json:"Array"`
    }
    
    func main() {
        var d response
        err := json.Unmarshal([]byte(`{"Items":{"A":1,"B":2,"C":3},"Array":[]}`), &d)
        if err != nil {
            panic(err)
        }
        fmt.Println(d)
    }
    

    输出:

    {map[C:3 A:1 B:2]} 
    

    您可以使用json.Marshaljson.Unmarshal,就像这个工作代码(C):

    package main
    
    import (
        "encoding/json"
        "fmt"
    )
    
    type Item int
    
    type response struct {
        Items map[string]Item `json:"Items"`
        Array []Item          `json:"Array"`
    }
    
    func main() {
        var test = response{
            Items: map[string]Item{"A": 1, "B": 2, "C": 3},
            Array: []Item{},
        }
        body, err := json.Marshal(test)
        if err != nil {
            panic(err)
        }
        fmt.Println(string(body)) // {"Items":{"A":1,"B":2,"C":3},"Array":[]}
    
        var d response
        err = json.Unmarshal(body, &d)
        if err != nil {
            panic(err)
        }
        fmt.Println(d)
    }
    

    输出:

    {"Items":{"A":1,"B":2,"C":3},"Array":[]}
    {map[A:1 B:2 C:3] []}
    

    您可以将{"A":1,"B":2,"C":3} 解组为map[A:1 B:2 C:3]
    "[1,2,3]"[1 2 3],就像这个工作代码(D):

    package main
    
    import (
        "encoding/json"
        "fmt"
    )
    
    type Item int
    
    type response1 map[string]Item
    type response2 []Item
    
    func main() {
        var d response1
        err := json.Unmarshal([]byte(`{"A":1,"B":2,"C":3}`), &d)
        if err != nil {
            panic(err)
        }
        fmt.Println(d) // map[A:1 B:2 C:3]
    
        var d2 response2
        err2 := json.Unmarshal([]byte(`[1,2,3]`), &d2)
        if err2 != nil {
            panic(err2)
        }
        fmt.Println(d2) // [1 2 3]
    }
    

    输出:

    map[A:1 B:2 C:3]
    [1 2 3]
    

    【讨论】:

      猜你喜欢
      • 2021-07-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-12-19
      • 2018-06-24
      • 2021-01-12
      相关资源
      最近更新 更多