无法在golang中解析复杂的json。

huangapple go评论115阅读模式
英文:

Unable to parse a complex json in golang

问题

{
"period": "yy",
"exec_period": {
"start": {
"month": 1,
"week": 2,
"day": 3,
"hour": 4,
"minute": 5
},
"end": {
"month": 6,
"week": 7,
"day": 8,
"hour": 9,
"minute": 10
}
},
"backup": [
{
"local_dir": "directoryLo1",
"server_dir": "directoryLo2",
"server_host": "domaineName"
},
{
"local_dir": "directoryLo1",
"server_dir": "directorySe2",
"server_host": "domaineName"
}
],
"incremental_save": "1Y2M"
}

英文:

I want to parse this JSON (in config/synch.conf):

  1. {
  2. "period" :"yy",
  3. "exec_period" :
  4. {
  5. "start" : {
  6. "month" : 1,
  7. "week" : 2,
  8. "day" : 3,
  9. "hour" : 4,
  10. "minute" : 5
  11. },
  12. "end" : {
  13. "month" : 6,
  14. "week" : 7,
  15. "day" : 8,
  16. "hour" : 9,
  17. "minute" : 10
  18. }
  19. },
  20. "backup" : [
  21. {
  22. "local_dir" : "directoryLo1",
  23. "server_dir" : "directoryLo2",
  24. "server_host" : "domaineName"
  25. },
  26. {
  27. "local_dir" : "directoryLo1",
  28. "server_dir" : "directorySe2",
  29. "server_host" : "domaineName"
  30. }
  31. ],
  32. "incremental_save" : "1Y2M"
  33. }

With this programm:

  1. package main
  2. import (
  3. "encoding/json"
  4. "fmt"
  5. "io/ioutil"
  6. )
  7. func main() {
  8. content, err := ioutil.ReadFile("config/synch.conf")
  9. if err == nil {
  10. type date struct{
  11. month float64
  12. week float64
  13. day float64
  14. hour float64
  15. minute float64
  16. }
  17. type period struct{
  18. start date
  19. end date
  20. }
  21. type backupType []struct{
  22. local_dir string
  23. server_dir string
  24. server_host string
  25. }
  26. type jason struct{
  27. period string
  28. exec_period period
  29. backup backupType
  30. incremental_save string
  31. }
  32. var parsedMap jason
  33. err := json.Unmarshal(content, &parsedMap)
  34. if err!= nil {
  35. fmt.Println(err)
  36. }
  37. fmt.Println(parsedMap)
  38. } else {
  39. panic(err)
  40. }
  41. }

Which doesn't work as expected, as the output is:

  1. { {{0 0 0 0 0} {0 0 0 0 0}} [] }

Here is the same example at play.golang.org
http://play.golang.org/p/XoMJIDIV59

I don't know if this is possible with go, but I wanted to get the value of the json.Unmarshal function stored in a map[string]interface{} (or another object that allows that) where I could access, for example, the value of the minute's end (10) like this: parsedMap["exec_period"]["end"]["minute"], but I don't uderstand the "Generic JSON withinterface{}" part of [JSON and Go][1] at golang.org

[1]: http://golang.org/doc/articles/json_and_go.html "JSON and Go"

答案1

得分: 13

你的代码很好,除了json包只能处理导出的字段之外。

如果你将每个字段名的首字母大写,一切都会正常工作:

  1. type date struct {
  2. Month float64
  3. Week float64
  4. Day float64
  5. Hour float64
  6. Minute float64
  7. }
  8. type period struct {
  9. Start date
  10. End date
  11. }
  12. type backupType []struct {
  13. Local_dir string
  14. Server_dir string
  15. Server_host string
  16. }
  17. type jason struct {
  18. Period string
  19. Exec_period period
  20. Backup backupType
  21. Incremental_save string
  22. }

虽然可以将其编组为map[string]interface{},但如果数据具有固定的结构(如你的问题中的结构),你的解决方案可能更可取。使用interface{}将需要类型断言,可能会变得混乱。你的示例将如下所示:

  1. parsedMap["exec_period"].(map[string]interface{})["end"].(map[string]interface{})["minute"].(float64)
英文:

Your code is fine except that the json package can only work with exported fields.

Everything will work if you capitalize the first letter for each field name:

  1. type date struct {
  2. Month float64
  3. Week float64
  4. Day float64
  5. Hour float64
  6. Minute float64
  7. }
  8. type period struct {
  9. Start date
  10. End date
  11. }
  12. type backupType []struct {
  13. Local_dir string
  14. Server_dir string
  15. Server_host string
  16. }
  17. type jason struct {
  18. Period string
  19. Exec_period period
  20. Backup backupType
  21. Incremental_save string
  22. }

While it is possible to marshal into a map[string]interface{}, if the data has a set structure (such as the one in your question), your solution is most likely preferable. Using interface{} would require type assertions and might end up looking messy. Your example would look like this:

  1. parsedMap["exec_period"].(map[string]interface{})["end"].(map[string]interface{})["minute"].(float64)

huangapple
  • 本文由 发表于 2013年6月20日 16:45:08
  • 转载请务必保留本文链接:https://go.coder-hub.com/17209111.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定