Golang XML marshal两个相同的属性

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

Golang XML marshal two identical attributes

问题

我被迫使用一些设计不良的 XML,我正在尝试将这个 XML 读入到一个 Go 结构中。这里是一些示例数据:

  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <dictionary>
  3. <direction from="lojban" to="English">
  4. <valsi word="cipni" type="gismo">
  5. <rafsi>cpi</rafsi>
  6. <definition>x1 is a bird of species x2</definition>
  7. <notes></notes>
  8. </valsi>
  9. ...
  10. </direction>
  11. <direction from="English" to="lojban">
  12. <nlword word="eagle" valsi="atkuila" />
  13. <nlword word="hawk" sense="bird" valsi="aksiptrina" />
  14. ...
  15. </direction>
  16. </dictionary>

我的问题是,我无法同时读取 <valsi> 节点和 <nlword> 节点,因为它们都包含属性 "word":

  1. main.NLWord 字段 "Word" 的标签 "word,attr" 与字段 "Valsi" 的标签 "word,attr" 冲突

我开始觉得解组可能不是正确的方法,因为我理想情况下会以不同的方式组织数据。我应该使用其他方法读取 XML 并手动构建数据结构吗?

  1. type Valsi struct {
  2. Word string `xml:"word,attr"`
  3. Type string `xml:"type,attr"`
  4. Def string `xml:"definition"`
  5. Notes string `xml:"notes"`
  6. Class string `xml:"selmaho"`
  7. Rafsi []string `xml:"rafsi"`
  8. }
  9. // 制作这个 XML 结构的人需要受到痛苦的教训...
  10. type Collection struct {
  11. From string `xml:"from"`
  12. To string `xml:"to"`
  13. Valsi []Valsi `xml:"valsi"`
  14. }
  15. type Vlaste struct {
  16. Direction []Collection `xml:"direction"`
  17. }
  18. var httpc = &http.Client{}
  19. func parseXML(data []byte) Vlaste {
  20. vlaste := Vlaste{}
  21. err := xml.Unmarshal(data, &vlaste)
  22. if err != nil {
  23. fmt.Println("Problem Decoding!")
  24. log.Fatal(err)
  25. }
  26. return vlaste
  27. }

希望这可以帮助到你。

英文:

I'm forced to work with some poorly designed XML, I'm trying to read this XML into a Go structure. Here's some sample data:

  1. &lt;?xml version=&quot;1.0&quot; encoding=&quot;UTF-8&quot;?&gt;
  2. &lt;dictionary&gt;
  3. &lt;direction from=&quot;lojban&quot; to=&quot;English&quot;&gt;
  4. &lt;valsi word=&quot;cipni&quot; type=&quot;gismo&quot;&gt;
  5. &lt;rafsi&gt;cpi&lt;/rafsi&gt;
  6. &lt;definition&gt;x1 is a bird of species x2&lt;/definition&gt;
  7. &lt;notes&gt;&lt;/notes&gt;
  8. &lt;/valsi&gt;
  9. ...
  10. &lt;/direction&gt;
  11. &lt;direction from=&quot;English&quot; to=&quot;lojban&quot;&gt;
  12. &lt;nlword word=&quot;eagle&quot; valsi=&quot;atkuila&quot; /&gt;
  13. &lt;nlword word=&quot;hawk&quot; sense=&quot;bird&quot; valsi=&quot;aksiptrina&quot; /&gt;
  14. ...
  15. &lt;/direction&gt;
  16. &lt;/dictionary&gt;

My issue is I can either read in <valsi> nodes or <nlword> because they both contain the attribute "word":

  1. main.NLWord field &quot;Word&quot; with tag &quot;word,attr&quot; conflicts with field &quot;Valsi&quot; with tag &quot;word,attr&quot;

I'm starting to think unmarshalling may be the wrong approach as I'd ideally structure the data differently. Should I read the XML in using some other method and build up data structures manually?

  1. type Valsi struct {
  2. Word string `xml:&quot;word,attr&quot;`
  3. Type string `xml:&quot;type,attr&quot;`
  4. Def string `xml:&quot;definition&quot;`
  5. Notes string `xml:&quot;notes&quot;`
  6. Class string `xml:&quot;selmaho&quot;`
  7. Rafsi []string `xml:&quot;rafsi&quot;`
  8. }
  9. //Whoever made this XML structure needs to be painfully taught a lesson...
  10. type Collection struct {
  11. From string `xml:&quot;from&quot;`
  12. To string `xml:&quot;to&quot;`
  13. Valsi []Valsi `xml:&quot;valsi&quot;`
  14. }
  15. type Vlaste struct {
  16. Direction []Collection `xml:&quot;direction&quot;`
  17. }
  18. var httpc = &amp;http.Client{}
  19. func parseXML(data []byte) Vlaste {
  20. vlaste := Vlaste{}
  21. err := xml.Unmarshal(data, &amp;vlaste)
  22. if err != nil {
  23. fmt.Println(&quot;Problem Decoding!&quot;)
  24. log.Fatal(err)
  25. }
  26. return vlaste
  27. }

答案1

得分: 2

我可能没有完全理解你的问题,但是对于我来说,以下结构在我这里运行良好(根据你修改的示例):

  1. type Valsi struct {
  2. Word string `xml:"word,attr"`
  3. Type string `xml:"type,attr"`
  4. Def string `xml:"definition"`
  5. Notes string `xml:"notes"`
  6. Class string `xml:"selmaho"`
  7. Rafsi []string `xml:"rafsi"`
  8. }
  9. type NLWord struct {
  10. Word string `xml:"word,attr"`
  11. Sense string `xml:"sense,attr"`
  12. Valsi string `xml:"valsi,attr"`
  13. }
  14. type Collection struct {
  15. From string `xml:"from,attr"`
  16. To string `xml:"to,attr"`
  17. Valsi []Valsi `xml:"valsi"`
  18. NLWord []NLWord `xml:"nlword"`
  19. }
  20. type Vlaste struct {
  21. Direction []Collection `xml:"direction"`
  22. }

在这个结构中,Collection 可以有 Valsi 值和 NLWord 值。
然后,你可以根据 From/ToValsiNLWord 的长度来决定如何处理数据。

英文:

I may not have grasped what your problem is but the following structure works fine for me
(your modified example on play):

  1. type Valsi struct {
  2. Word string `xml:&quot;word,attr&quot;`
  3. Type string `xml:&quot;type,attr&quot;`
  4. Def string `xml:&quot;definition&quot;`
  5. Notes string `xml:&quot;notes&quot;`
  6. Class string `xml:&quot;selmaho&quot;`
  7. Rafsi []string `xml:&quot;rafsi&quot;`
  8. }
  9. type NLWord struct {
  10. Word string `xml:&quot;word,attr&quot;`
  11. Sense string `xml:&quot;sense,attr&quot;`
  12. Valsi string `xml:&quot;valsi,attr&quot;`
  13. }
  14. type Collection struct {
  15. From string `xml:&quot;from,attr&quot;`
  16. To string `xml:&quot;to,attr&quot;`
  17. Valsi []Valsi `xml:&quot;valsi&quot;`
  18. NLWord []NLWord `xml:&quot;nlword&quot;`
  19. }
  20. type Vlaste struct {
  21. Direction []Collection `xml:&quot;direction&quot;`
  22. }

In this structure, Collection can have Valsi values as well as NLWord values.
You can then decide, depending on From/To or the length of either Valsi or NLWord how to handle the data.

huangapple
  • 本文由 发表于 2013年10月18日 06:36:09
  • 转载请务必保留本文链接:https://go.coder-hub.com/19438495.html
匿名

发表评论

匿名网友

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

确定