我尝试了以下代码,以便了解为什么我在golang中遇到xml问题。
据我所知,我应该能够编组一个结构,然后将结果数据解组成一个相同类型的结构?
结果我期望的是一个包含一片子节点的父结构,而不是子切片是nil?
package main
import (
"encoding/xml"
"fmt"
)
type Parent struct {
XMLName xml.Name `xml:"parent"`
Children []Child `xml:"children"`
}
type Child struct {
XMLName xml.Name `xml:"child"`
ID int `xml:"ID"`
}
func main() {
children := make([]Child, 3)
for i := range children {
children[i] = Child{ID: i}
}
p1 := Parent{Children: children}
data, err := xml.Marshal(p1)
if err != nil {
fmt.Printf("Error during marshal: %v\n", err)
}
fmt.Printf("Raw XML: %v\n", string(data))
p2 := Parent{}
err = xml.Unmarshal(data, &p2)
if err != nil {
fmt.Printf("Error during unmarshal: %v\n", err)
}
fmt.Printf("Unmarshalled struct: %v\n", p2)
}
答案 0 :(得分:1)
它的工作原理不是这样的:结构和XML之间没有临时双射。
E.g。您生成以下XML
<parent><child><ID>0</ID></child><child><ID>1</ID></child></parent>
因为您的Child
类型的字段XMLName xml.Name
带有xml标记&#34; child&#34;。
这就是Marshaling的工作方式。来自http://tip.golang.org/pkg/encoding/xml/#Marshal
XML元素的名称取自优先顺序:
- XMLName字段上的标记,如果数据是结构
- xml.Name
类型的XMLName字段的值- 用于获取数据的struct字段的标记
- 用于获取数据的struct字段的名称
- 编组类型的名称
现在看看如果您尝试解组它会发生什么:
您的Parent
类型将其字段Children []Child
标记为&#34; children&#34;
但是您的XML内部没有<children>
标记,只有<child>
。
如果您使用
type Parent struct {
XMLName xml.Name `xml:"parent"`
Children []Child `xml:"child"` // "child", not "children"
}
它的工作方式与您的意图相同。