[英]How to Unmarshal list of varied types without defaulting to float64
我有以下json數據(來自外部程序,簡化了一點),我無法更改json格式。
[1416495600501595942, {"venue_id": 73, "message_type": "ABC", "sequence": 26686695}]
我在使用Go打包時遇到了麻煩,主要是因為它是不同類型的列表。 似乎要做的顯而易見的事情是[] interface {},它可以工作,但是將其轉換為float64會產生我無法處理的舍入錯誤(該數字是自nanos中的紀元以來的時間戳) )。
我可以通過兩次解壓縮來使它工作,例如[] interface {}和[] int64,但這顯然會阻礙性能,並且我正在實時處理大量數據。 我在這里嘗試使用struct,因為它將被視為地圖,而不是列表[]
有什么方法可以將其傳遞為數據格式,或者將其默認設置為int64而不是float64嗎? 永遠都是
[int64, map[string]interface{}]
即我知道上級列表的格式,並且映射的鍵是字符串,但是值可以是任何值(很痛苦,包括小數,我認為我唯一可以用來將它們解釋為float的東西.. 。)
package main
import (
"encoding/json"
"fmt"
)
func main() {
j := `[1416495600501595942, {"venue_id": 73, "message_type": "ABC", "sequence": 26686695}]`
b := []byte(j)
fmt.Println(j)
var line []interface{}
var ints []int64
json.Unmarshal(b, &line)
fmt.Println(line)
// fmt.Println(line[0].(int64)) - this doesn't work
fmt.Println(line[0].(float64))
fmt.Println(int64(line[0].(float64)))
json.Unmarshal(b, &ints)
fmt.Println(ints)
}
輸出如下:
[1416495600501595942, {"venue_id": 73, "message_type": "oKC", "sequence": 26686695}] [1.416495600501596e+18 map[venue_id:73 message_type:oKC sequence:2.6686695e+07]] 1.416495600501596e+18 1416495600501595904 [1416495600501595942 0]
解決方法(感謝Makpoc / dystroy)
package main
import (
"encoding/json"
"fmt"
"bytes"
)
func main() {
j := `[1416495600501595942, {"venue_id": 7.3, "message_type": "oKC", "sequence": 26686695}]`
b := []byte(j)
fmt.Println(j)
var line []interface{}
d := json.NewDecoder(bytes.NewBuffer(b))
d.UseNumber()
if err := d.Decode(&line); err != nil {
panic(err)
}
fmt.Println(line[0])
data := line[1].(map[string]interface{})
fmt.Println(data["venue_id"])
fmt.Println(data["sequence"])
}
根據此答案,您可以使用Decoder->和UseNumber或結構來代替直接解析值。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.