将单个字段分别编组为两个标签在golang中

huangapple go评论114阅读模式
英文:

Marshal single field into two tags in golang

问题

尝试理解一种为结构化为以下形式的XML创建自定义编组器的方法:

  1. <!-- language: lang-xml -->
  2. <Appointment>
  3. <Date>2004-12-22</Date>
  4. <Time>14:00</Time>
  5. </Appointment>

我在考虑这样的解决方案:

  1. <!-- language: lang-go -->
  2. type Appointment struct {
  3. DateTime time.Time `xml:"???"`
  4. }

问题是,我应该在"???"的位置放什么,才能将一个字段保存到两个不同的XML标签中?

英文:

Trying to understand a way to create custom marshaller for xml structured as:

<!-- language: lang-xml -->

  1. &lt;Appointment&gt;
  2. &lt;Date&gt;2004-12-22&lt;/Date&gt;
  3. &lt;Time&gt;14:00&lt;/Time&gt;
  4. &lt;/Appointment&gt;

I'm thinking of something like:

<!-- language: lang-go -->

  1. type Appointment struct {
  2. DateTime time.Time `xml:&quot;???&quot;`
  3. }

Question is, what would i put instead of ??? to have a single field be saved into two different xml tags?

答案1

得分: 3

复杂的编组/解组行为通常需要满足Marshal/Unmarshal接口(这对于XML、JSON和类似设置的Go类型都是如此)。

您需要使用MarshalXML()函数满足xml.Marshaler接口,类似以下示例:

  1. package main
  2. import (
  3. "encoding/xml"
  4. "fmt"
  5. "time"
  6. )
  7. type Appointment struct {
  8. DateTime time.Time
  9. }
  10. type appointmentExport struct {
  11. XMLName struct{} `xml:"appointment"`
  12. Date string `xml:"date"`
  13. Time string `xml:"time"`
  14. }
  15. func (a *Appointment) MarshalXML(e *xml.Encoder, start xml.StartElement) error {
  16. n := &appointmentExport{
  17. Date: a.DateTime.Format("2006-01-02"),
  18. Time: a.DateTime.Format("15:04"),
  19. }
  20. return e.Encode(n)
  21. }
  22. func main() {
  23. a := &Appointment{time.Now()}
  24. output, _ := xml.MarshalIndent(a, "", " ")
  25. fmt.Println(string(output))
  26. }
  27. // 输出:
  28. // <appointment>
  29. // <date>2016-04-15</date>
  30. // <time>17:43</time>
  31. // </appointment>

以上代码将输出XML格式的字符串。

英文:

Complex marshaling/unmarshaling behavior generally requires satisfying a Marshal/Unmarshal interface (this is of true of XML, JSON, and similarly setup types in go).

You'd need to satisfy the xml.Marshaler interface with a MarshalXML() function, something like the following:

  1. package main
  2. import (
  3. &quot;encoding/xml&quot;
  4. &quot;fmt&quot;
  5. &quot;time&quot;
  6. )
  7. type Appointment struct {
  8. DateTime time.Time
  9. }
  10. type appointmentExport struct {
  11. XMLName struct{} `xml:&quot;appointment&quot;`
  12. Date string `xml:&quot;date&quot;`
  13. Time string `xml:&quot;time&quot;`
  14. }
  15. func (a *Appointment) MarshalXML(e *xml.Encoder, start xml.StartElement) error {
  16. n := &amp;appointmentExport{
  17. Date: a.DateTime.Format(&quot;2006-01-02&quot;),
  18. Time: a.DateTime.Format(&quot;15:04&quot;),
  19. }
  20. return e.Encode(n)
  21. }
  22. func main() {
  23. a := &amp;Appointment{time.Now()}
  24. output, _ := xml.MarshalIndent(a, &quot;&quot;, &quot; &quot;)
  25. fmt.Println(string(output))
  26. }
  27. // prints:
  28. // &lt;appointment&gt;
  29. // &lt;date&gt;2016-04-15&lt;/date&gt;
  30. // &lt;time&gt;17:43&lt;/time&gt;
  31. // &lt;/appointment&gt;

答案2

得分: 0

快速猜测,你不能。你应该使用你的Appointment类型实现xml.Marshaler接口...

英文:

Quick guess, you can't. You should implement the xml.Marshaler interface with your Appointment type…

huangapple
  • 本文由 发表于 2016年4月13日 20:59:22
  • 转载请务必保留本文链接:https://go.coder-hub.com/36599180.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定