在 Go (Golang) 中使用 XML:encoding/xml 包详细指南
在现代 Go (Golang) 开发中,处理 XML 数据的任务相当常见——从与遗留系统集成到在 SOAP 服务中交换数据。Go 标准库提供了强大且灵活的 encoding/xml 包,可以高效地解析、创建和转换 XML 文档。在本文中,我们将详细分析在 Go 中使用 XML 的所有关键功能。
encoding/xml 包的主要功能
encoding/xml 包提供了一个简单的接口,用于将 Go 结构体序列化(编组)为 XML,以及将 XML 反序列化(解组)回结构体。它支持:
- 将 Go 结构体转换为 XML 文档,反之亦然
- 处理属性、嵌套元素和命名空间
- 通过
xml.Decoder流式解析大型 XML 文件 - 通过结构体标签自定义序列化规则
安装和导入包
encoding/xml 包是 Go 标准库的一部分,因此无需额外安装。使用时只需导入它:
import ( "encoding/xml" "fmt" "os")编组:Go 结构体 → XML
要将 Go 结构体转换为 XML,使用 xml.Marshal() 函数,或使用 xml.MarshalIndent() 进行格式化输出。看一个示例:
type Person struct { XMLName xml.Name `xml:"person"` ID int `xml:"id,attr"` FirstName string `xml:"name>first"` LastName string `xml:"name>last"` Age int `xml:"age"`}
func main() { p := Person{ ID: 123, FirstName: "伊万", LastName: "彼得罗夫", Age: 30, }
output, err := xml.MarshalIndent(p, "", " ") if err != nil { fmt.Printf("编组错误:%v", err) return }
fmt.Println(string(output))}执行结果:
<person id="123"> <name> <first>伊万</first> <last>彼得罗夫</last> </name> <age>30</age></person>解组:XML → Go 结构体
反向过程——将 XML 数据转换为 Go 结构体——使用 xml.Unmarshal() 完成:
func unmarshalExample() { xmlData := `<person id="456"> <name> <first>玛丽亚</first> <last>西多罗娃</last> </name> <age>25</age></person>`
var p Person err := xml.Unmarshal([]byte(xmlData), &p) if err != nil { fmt.Printf("解组错误:%v", err) return }
fmt.Printf("ID: %d, 姓名:%s %s, 年龄:%d", p.ID, p.FirstName, p.LastName, p.Age) // 输出:ID: 456, 姓名:玛丽亚 西多罗娃, 年龄:25}处理属性和嵌套元素
encoding/xml 包使用结构体标签来控制映射。标签的主要指令:
xml:"name"— 元素名称xml:"name,attr"— 元素属性xml:"parent>child"— 嵌套元素xml:",chardata"— 文本内容xml:",innerxml"— 元素内的原始 XMLxml:",comment"— XML 注释xml:"-"— 忽略字段
流式解析大型 XML 文件
为了处理大型 XML 文档(例如,大小为 GB 级的文件),使用流式解析器 xml.Decoder。这允许不加载整个文档到内存中,而是逐步处理数据。