xml - 使用冲突的元素名称在 Go 中解码 XML

标签 xml encoding go marshalling unmarshalling

我有以下 XML,外部定义且不受我的组织控制:

<foo>
  <bar>
    <zip>zip</zip>
  </bar>
  <bar>
    <zap>zap</zap>
  </bar>
</foo>

我正在使用这些结构:

type Foo struct {
    XMLName xml.Name `xml:"foo"`
    Bar1    Bar1
    Bar2    Bar2
}

type Bar1 struct {
    XMLName xml.Name `xml:"bar"`
    Zip     string   `xml:"zip"`
}

type Bar2 struct {
    XMLName xml.Name `xml:"bar"`
    Zap     string   `xml:"zap"`
}

由于“bar”名称冲突,没有任何内容被解码。如何填充 Bar1 和 Bar2 结构?

这是我的:https://play.golang.org/p/D2IRLojcTB

这是我想要的结果:https://play.golang.org/p/Ytrbzzy9Ok

在第二个中,我将第二个“bar”更新为“bar1”,一切正常。我宁愿想出一个更简洁的解决方案来修改传入的 XML。

最佳答案

encoding/xml包将无法完全按照您的意愿进行操作,因为它决定了 Foo 的哪个字段当它遇到 <bar> 时解码成元素,而不是在处理该元素的子元素时。您的结构定义使这个决定变得模棱两可,因为来自 xml.Unmarshal 的错误表示:

main.Foo field "Bar1" with tag "" conflicts with field "Bar2" with tag ""

这里有两个可行的替代方案:

<强>1。使用一个 Bar覆盖两个分支的结构

如果您将类型修改为:

type Foo struct {
    XMLName xml.Name `xml:"foo"`
    Bars    []Bar    `xml:"bar"`
}

type Bar struct {
    Zip string `xml:"zip"`
    Zap string `xml:"zap"`
}

您现在将获得代表所有 <bar> 的 slice 元素。您可以判断该元素是否有 <zip><zap>通过检查相应字段是否为非空元素。

您可以在此处试用此版本:https://play.golang.org/p/kguPCYmKX0

<强>2。使用子选择器

如果您只对<bar> 的单个子元素感兴趣在每个分支中,那么您可能根本不需要结构来表示该元素。例如,您可以解码为以下类型:

type Foo struct {
    XMLName xml.Name `xml:"foo"`
    Zip     string   `xml:"bar>zip"`
    Zap     string   `xml:"bar>zap"`
}

现在 <bar> 的 children 元素将被直接解码为 Foo 的成员结构。请注意,使用此选项您将无法将您选择的输入与例如

<foo>
  <bar>
    <zip>zip</zip>
    <zap>zap</zap>
  </bar>
</foo>

如果这会导致问题,那么您应该选择第一个解决方案。

您可以在此处试用此版本:https://play.golang.org/p/fAE_HSrv4y

关于xml - 使用冲突的元素名称在 Go 中解码 XML,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28954415/

相关文章:

grails - Groovy确定字节数组编码

java - 如何使用 Spring/Roo 为 POST 编码特殊字符

go - Updates() 似乎没有更新关联

java - 使用 xml dom 解析器获取元素

c# - 如何检查此 C# LINQ to XML 语句中的 NullReferenceException?

c# - 从 Google 距离矩阵 API C# 中读取值

c# - 在没有 <string>/XML 的情况下需要 JSON 中的 webService

mysql - 如何使用 ASCII 查询 mysql utf-8 表

performance - 计数 byte slice 中所有非零字节的最快方法是什么

go - 如何将引导样式应用于自动生成的表单