gpt4 book ai didi

xml - 将子元素的属性直接解析为 Go struct

转载 作者:IT王子 更新时间:2023-10-29 02:33:33 43 4
gpt4 key购买 nike

在使用 Go 解析 XML 时,如何将嵌套元素的属性直接读取到我的结构中?

我的 XML 如下所示。它是 OpenStreetMap 格式的一部分:

<way id="123" >
<nd ref="101"/>
<!-- Lots of nd elements repeated -->
<nd ref="109"/>
</way>

我有

type Way struct {
Nodes []NodeRef `xml:"nd"`
}

type NodeRef struct {
Ref int `xml:"ref,attr"`
}

但我希望能够做到

type Way struct {
Nodes []int `???`
}

直接。

关于 Unmarshalling 的文档没有帮助我。我试过使用 xml:"nd>ref,attr" 但失败并显示“chain not valid with attr flag”。

请看下面的示例代码。 Run the code in Go Playground

package main

import (
"encoding/xml"
"fmt"
"io"
"os"
"strings"
)

func main() {
data := `
<way id="5090250" >
<nd ref="822403"/>
<nd ref="21533912"/>
<nd ref="821601"/>
<nd ref="21533910"/>
<nd ref="135791608"/>
<nd ref="333725784"/>
<nd ref="333725781"/>
<nd ref="333725774"/>
<nd ref="333725776"/>
<nd ref="823771"/>
</way>
`

r := strings.NewReader(data)
way, err := ReadWay(r)
if err != nil {
fmt.Println("Could not read", err)
os.Exit(1)
}

fmt.Println(way)
}

// I'd like to get rid of this nested struct.
type NodeRef struct {
Ref int `xml:"ref,attr"`
}

type Way struct {
ID int `xml:"id,attr"`
// How can I write all <nd ref="123"/> directly into Nodes []int?
Nodes []NodeRef `xml:"nd"`
}

func ReadWay(reader io.Reader) (Way, error) {
var way Way
if err := xml.NewDecoder(reader).Decode(&way); err != nil {
return way, err // Why can't I return nil, err?
}
return way, nil
}

最佳答案

简而言之,您不能直接这样做。绕过 XML 结构的常见模式是实现 xml.Unmarshaler 接口(interface)。这是一个例子:

type Way struct {
ID int
Nodes []int
}

func (w *Way) UnmarshalXML(d *xml.Decoder, start xml.StartElement) error {
var payload struct {
ID int `xml:"id,attr"`
Nodes []struct {
Ref int `xml:"ref,attr"`
} `xml:"nd"`
}

err := d.DecodeElement(&payload, &start)
if err != nil {
return err
}

w.ID = payload.ID
w.Nodes = make([]int, 0, len(payload.Nodes))

for _, node := range payload.Nodes {
w.Nodes = append(w.Nodes, node.Ref)
}

return nil
}

在这里,payload 变量是根据您的 XML 数据建模的,而 Way 结构是按照您希望的方式建模的。解码有效负载后,您可以根据需要使用它来初始化 Way 变量……

旁注: //为什么我不能返回 nil,呃?

您不能返回 nil 因为 Way 既不是指针也不是接口(interface),因此 nil 不是有效值

关于xml - 将子元素的属性直接解析为 Go struct,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36279414/

43 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com