猿问

使用 Golang 进行 XML 编组 - 具有相同节点名称的多个节点

在VAST规范中,一个 XML 文件可能包含多个具有相同名称的节点 - 例如,多个Impression节点的不同之处仅在于它们的id.


考虑以下示例:


<?xml version="1.0" encoding="UTF-8"?>

<VAST xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="2.0" xsi:noNamespaceSchemaLocation="vast.xsd">

   <Ad id="812030">

      <InLine>

         <AdSystem>FT</AdSystem>

         <AdTitle>Flashtalking mobile vast template 2.0</AdTitle>

         <Description>date of revision 10-04-14</Description>

         <Impression id="ft_vast_i"><![CDATA[http://servedby.flashtalking.com/imp/1/31714;812030;201;gif;DailyMail;640x360VASTHTML5/?ft_creative=377314&ft_configuration=0&cachebuster=1076585830]]></Impression>

         <Impression id="3rdparty" />

         <Impression id="3rdparty" />

         <Impression id="3rdparty" />

         <Impression id="3rdparty" />

         <Impression id="3rdparty" />

         <Impression id="3rdparty" />

         <Creatives>

            <Creative sequence="1">

               <Linear>

                  <Duration>00:00:15</Duration>

                  <TrackingEvents>

                  </TrackingEvents>

                  <VideoClicks>

                  </VideoClicks>

                  <MediaFiles>

                  </MediaFiles>

               </Linear>

            </Creative>

            <Creative sequence="1">

               <CompanionAds />

            </Creative>

         </Creatives>

      </InLine>

   </Ad>

</VAST>

注意多个Impression节点,它们的不同之处仅在于它们的id属性(事实上,有时甚至可能是相同的)。


有没有办法用 Golang 来表示这种结构,以保持使用encoding/xml包对 xml 进行编组和解组的能力?


冉冉说
浏览 155回答 2
2回答

蛊毒传说

对于重复的 XML 标签,只需在 Go 中使用切片即可。请参阅这个简单的示例,它处理您的 XML 输入,重点是解组<Impression>标签,然后再次对其进行编组:type Impression struct {&nbsp; &nbsp; Id&nbsp; &nbsp; &nbsp; string `xml:"id,attr"`&nbsp; &nbsp; Content string `xml:",chardata"`}type VAST struct {&nbsp; &nbsp; Impressions []Impression `xml:"Ad>InLine>Impression"`}func main() {&nbsp; &nbsp; v := &VAST{}&nbsp; &nbsp; if err := xml.Unmarshal([]byte(src), v); err != nil {&nbsp; &nbsp; &nbsp; &nbsp; panic(err)&nbsp; &nbsp; }&nbsp; &nbsp; fmt.Printf("%+v\n\n", v)&nbsp; &nbsp; if out, err := xml.MarshalIndent(v, "", "&nbsp; "); err != nil {&nbsp; &nbsp; &nbsp; &nbsp; panic(err)&nbsp; &nbsp; } else {&nbsp; &nbsp; &nbsp; &nbsp; fmt.Println(string(out))&nbsp; &nbsp; }}输出(已包装,在Go Playground上尝试):&{Impressions:[{Id:ft_vast_i Content:http://servedby.fla...[CUT]...1076585830}&nbsp;{Id:3rdparty Content:} {Id:3rdparty Content:} {Id:3rdparty Content:}&nbsp;{Id:3rdparty Content:} {Id:3rdparty Content:} {Id:3rdparty Content:}]}<VAST>&nbsp; <Ad>&nbsp; &nbsp; <InLine>&nbsp; &nbsp; &nbsp; <Impression id="ft_vast_i">http://servedby.fla...[CUT]...1076585830</Impression>&nbsp; &nbsp; &nbsp; <Impression id="3rdparty"></Impression>&nbsp; &nbsp; &nbsp; <Impression id="3rdparty"></Impression>&nbsp; &nbsp; &nbsp; <Impression id="3rdparty"></Impression>&nbsp; &nbsp; &nbsp; <Impression id="3rdparty"></Impression>&nbsp; &nbsp; &nbsp; <Impression id="3rdparty"></Impression>&nbsp; &nbsp; &nbsp; <Impression id="3rdparty"></Impression>&nbsp; &nbsp; </InLine>&nbsp; </Ad></VAST>

鸿蒙传说

是的,您可以编组/解组多个具有相同名称的节点。只需使用切片。看一下例子中的Email切片encoding/xml:type Email struct {&nbsp; &nbsp; Where string `xml:"where,attr"`&nbsp; &nbsp; Addr&nbsp; string}type Address struct {&nbsp; &nbsp; City, State string}type Result struct {&nbsp; &nbsp; XMLName xml.Name `xml:"Person"`&nbsp; &nbsp; Name&nbsp; &nbsp; string&nbsp; &nbsp;`xml:"FullName"`&nbsp; &nbsp; Phone&nbsp; &nbsp;string&nbsp; &nbsp; Email&nbsp; &nbsp;[]Email&nbsp; &nbsp; Groups&nbsp; []string `xml:"Group>Value"`&nbsp; &nbsp; Address}以及相应的 XML 文档:<Person>&nbsp; <FullName>Grace R. Emlin</FullName>&nbsp; <Company>Example Inc.</Company>&nbsp; <Email where="home">&nbsp; &nbsp; <Addr>gre@example.com</Addr>&nbsp; </Email>&nbsp; <Email where='work'>&nbsp; &nbsp; <Addr>gre@work.com</Addr>&nbsp; </Email>&nbsp; <Group>&nbsp; &nbsp; <Value>Friends</Value>&nbsp; &nbsp; <Value>Squash</Value>&nbsp; </Group>&nbsp; <City>Hanga Roa</City>&nbsp; <State>Easter Island</State></Person>
随时随地看视频慕课网APP

相关分类

Go
我要回答