如何解组包含整数,浮点数和数字字符串的JSON?

时间:2019-04-16 18:31:49

标签: json go

我有多个不同的JSON数据请求,这些请求正在传递到包含不同格式数字的Go应用程序中。请求的示例如下:

{
    "stringData":"123456",
    "intData": 123456,
    "floatData": 123456.0
}

是否有一种方法可以将此数据解组为由JSON数据确定的类型。例如,字符串数据将为“ 123456”,整数数据将为123456,浮点数据将为123456.0。我没有为这些JSON对象定义结构,因此不能为这些对象创建结构。

我已经看过解码器.UseNumber()方法将数据转换为字符串,但是之后我不知道如何处理stringData和intData之间的差异。

2 个答案:

答案 0 :(得分:1)

您可以将json解组到map [string] interface {},然后使用type switch强制转换为正确的类型。

答案 1 :(得分:1)

Decode to map[string]interface{} with the UseNumber option. Use a type assertion to find numbers and convert based on presence of the ".".

dec := json.NewDecoder(r)
dec.UseNumber()

var m map[string]interface{}
err := dec.Decode(&m)
if err != nil {
    log.Fatal(err)
}

for k, v := range m {
    v, err := decodeValue(v)
    if err != nil {
        log.Fatal(err)
    }
for k, v := range m {
    v, err := decodeValue(v)
    if err != nil {
        log.Fatal(err)
    }
    switch v := v.(type) {
    case string:
        fmt.Printf("%s is a string with value %q\n", k, v)
    case int64:
        fmt.Printf("%s is a integer with value %d\n", k, v)
    case float64:
        fmt.Printf("%s is a float with value %f\n", k, v)
    default:
        fmt.Printf("%s is a %T with value %v\n", k, v, v)
    }
}


...

func decodeValue(v interface{}) (interface{}, error) {
    if vv, ok := v.(json.Number); ok {
        if strings.Contains(vv.String(), ".") {
            return vv.Float64()
        } else {
            return vv.Int64()
        }
    } else {
        return v, nil
    }
}

Run it on the playground.

This example prints what's found and exits the program on error. If your goal is to create a map with the values of the correct types, then replace the code that prints numbers with m[k] = n.