英文:
Nested data structures in Go - Python equivalent
问题
我可以很容易地在Python中创建这个数据结构:
data = {'Locations': [],
'Dates': [],
'Properties': [{'key': 'data1', 'value': 'data2'}],
'Category': 'all'}
然后可以很容易地将其转换为JSON格式。例如:
import json
print(json.dumps(data))
输出结果为:
{"Category": "all", "Dates": [], "Locations": [], "Properties": [{"value": "data2", "key": "data1"}]}
然而,我正在尝试在Go语言中创建相同的结构并将其转换为JSON,但是我无法让结构包含应该包围属性元素的方括号。
import (
"fmt"
"encoding/json"
)
func main() {
data := map[string]interface{}{
"Offset": "0",
"Properties": map[string]string{"value": "data2", "key": "data1"},
"Category": "all",
"Locations": []string{},
"Dates": []string{},
}
data_json, _ := json.Marshal(data)
fmt.Println(string(data_json))
}
输出结果为:
{"Category":"all","Dates":[],"Locations":[],"Offset":"0","Properties":{"key":"data1","value":"data2"}}
这是一个演示:http://play.golang.org/p/49Kytg6v_C
英文:
I can create this data structure in Python really easily:
data = {'Locations': [],
'Dates': [],
'Properties': [{'key': 'data1', 'value': 'data2'}],
'Category': 'all'}
Which can then be marshalled to JSON in Python just as easily. e.g.
print json.dumps(data)
{"Category": "all", "Dates": [], "Locations": [], "Properties": [{"value": "data2", "key": "data1"}]}
However, I'm tearing my hair out trying to create the same structure then convert it to JSON in Go. Go looks to be very promising and just what I need for creating cross platform applications, but boy this stuff seems to be frustratingly difficult.
This is what I've tried, however I cant get the structure to include the square brackets that should surround the properties element.
import (
"fmt"
"encoding/json"
)
func main() {
data := map[string]interface{}{"Offset": "0", "Properties": map[string]string{"value": "data2", "key": "data1"}, "Category": "all", "Locations": []string{}, "Dates": []string{} }
data_json, _ := json.Marshal(data)
fmt.Println(string(data_json))
}
Which outputs:
{"Category":"all","Dates":[],"Locations":[],"Offset":"0","Properties":{"key":"data1","value":"data2"}}
Heres a demo: http://play.golang.org/p/49Kytg6v_C
答案1
得分: 2
你只需要创建一个 map[string]string
的切片:
data := map[string]interface{}{
"Offset": "0",
"Properties": []map[string]string{{"value": "data2", "key": "data1"}},
"Category": "all",
"Locations": []string{},
"Dates": []string{},
}
英文:
You just need to create a slice of map[string]string
:
data := map[string]interface{}{
"Offset": "0",
"Properties": []map[string]string{{"value": "data2", "key": "data1"}},
"Category": "all",
"Locations": []string{},
"Dates": []string{},
}
答案2
得分: 2
虽然 OneOfOne 的解决方案在字面上是可行的,但由于 Go 的静态类型特性,你可能想要使用结构体。
// `json:"stuff"` 会在读取或写入 JSON 时使用该 JSON 标签。
type Property struct {
Key string `json:"key"`
Val string `json:"value"`
}
// ,omitempty 允许在写入 JSON 时忽略空字符串 "",
// 我在这里加上它是因为你的 JSON 示例中的一个字段没有 Offset 字段
// 你也可以对其他字段使用它。
type MyType struct {
Offset string `json:",omitempty"`
Properties []Property
Category string
Locations []string
Dates []string
}
当然,你也可以考虑使用内置的或自定义的 Go 类型来表示其中一些字段,例如在 Dates 字段中使用 []time.Time
。这样做会使得随意读取/写入任意 JSON 数据变得更加困难,但由于你需要在某个地方编写一些逻辑来解释这些字段,在 Go 中通常更合理的做法是大部分时间将其视为一个结构体。
要读取/写入 JSON,你可以这样做:
import "encoding/json"
//...
stuff := MyType{}
json.Unmarshal(myJsonData, &stuff)
// 现在 stuff 是 { [{data1 data2}] all [] []}
out, _ := json.Marshal(stuff)
// string(out) 现在是 { "Properties":[{"key":"data1","value":"data2"}],
// "Category":"all","Locations":[],"Dates":[]}
Playground: http://play.golang.org/p/jIHgXmY13R
英文:
While OneOfOne's solution works in a literal sense, with Go's static typing you likely want a struct.
// The `json:"stuff"` will cause it to use that json tag when reading or writing json.
type Property struct {
Key string `json:"key"`
Val string `json:"value"`
}
// ,omitempty allows it to ignore the empty string "" when writing json,
// I put this here because one of your json examples had no Offset field
// you can do this with other fields too.
type MyType struct {
Offset string `json:",omitempty"`
Properties []Property
Category string
Locations []string
Dates []string
}
Of course, you could also consider using built-in or custom Go types for some of those fields, such as using a []time.Time
for the Dates field. This makes it more difficult to just read/write arbitrary json ad-hoc or on the fly, but since you need to have some logic somewhere to interpret those fields, in Go it generally makes much more sense to treat it as a struct most of the time.
To read in/put out the json, you would then do
import "encoding/json"
//...
stuff := MyType{}
json.Unmarshal(myJsonData, &stuff)
// stuff is now { [{data1 data2}] all [] []}
out,_ := json.Marshal(stuff)
// string(out) is now {"Properties":[{"key":"data1","value":"data2"}],
// "Category":"all","Locations":[],"Dates":[]}
Playground: http://play.golang.org/p/jIHgXmY13R
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论