xmlserializer的属性和多个元素

时间:2012-12-03 16:18:18

标签: c# xml

如何使用XmlSerializer

序列化以下结构
  1. 只有Product

  2. 的一个实例
  3. 只有Updates

  4. 的一个实例
  5. Updates可以包含多个Item

  6. Item可以包含多个Artifact

  7. XML:

    <Product>
        <Cycle Type = "x0446" />
        <Brand Type = "z773g" Include="All" />
        <Updates>
            <Item Name = "Foo">
                <Artifact Kind="6" Action="3" />
            </Item>
            <Item Name = "Bar">
                <Artifact Kind="6" Action="3" />
                <Artifact Kind="53" Action="3" />
            </Item>
        </Updates>
    </Product>
    

4 个答案:

答案 0 :(得分:3)

你可以在数组或List属性上使用[XmlElement]属性,而XmlSerializer足够聪明,可以接收它并将它们一个接一个地列在你的xml中。

您可以将Visual Studio XML-to-class生成器用于更复杂的结构: - 单击Windows中的开始菜单 - 点击“所有程序” - 找到Microsoft Visual Studio文件夹并单击它 - 单击Visual Studio Tools文件夹 - 单击开发人员命令提示符... - 假设你的xml保存在C:\ test \ Sample.xml中 - 输入“xsd C:\ test \ Sample.xml / out:C:\ test”   这应该通知您已创建架构。 - 输入“xsd C:\ test \ Sample.xsd / c / out:C:\ test”   这应该告诉你一个.cs类是为你创建的,在你的解决方案中复制它,可能更改命名空间(或者使用xsd命令参数) - 创建的类可能名称奇怪且更难以使用,如果您有复杂的XML或模式,请使用此方法。 - 您可以使用部分类扩展生成的代码(查找),不要直接修改生成的代码

-

这是直接代码(未生成)的样子:

public class Product{
    [XmlElement]
    public Cycle Cycle {get;set;}

    [XmlElement]
    public Brand Brand {get;set;}

    [XmlElement]
    public Updates Updates {get;set;}
}

public class Updates{
    [XmlElement("Item")]
    public UpdateItem[] Items{get;set;}
}

public class UpdateItem{ 
    [XmlAttribute]
    public string Name{get;set;} // use [XmlAttribute] in Cycle, Brand and Artifact classes

    [XmlElement("Artifact")]
    public Artifact[] Artifact{get;set;} 
}
//.... etc

以下是生成的代码:

/// <remarks/>
[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.0.30319.17929")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(AnonymousType=true)]
public partial class ProductUpdatesItem {

private ProductUpdatesItemArtifact[] artifactField;

private string nameField;

/// <remarks/>
[System.Xml.Serialization.XmlElementAttribute("Artifact", Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
public ProductUpdatesItemArtifact[] Artifact {
    get {
        return this.artifactField;
    }
    set {
        this.artifactField = value;
    }
}

[/代码]

答案 1 :(得分:1)

你可以control xml serialization using attributes。使用XmlAttribute属性将默认序列化作为元素更改为序列化作为属性。使用XmlElement属性将列表序列化为xml元素的平面序列。

public class Product
{
    public Cycle Cycle { get; set; }
    public Brand Brand { get; set; }
    public List<Item> Updates { get; set; }
}

public class Cycle
{
    [XmlAttribute("Type")]
    public string Type { get; set; }    
}

public class Brand
{
    [XmlAttribute("Type")]
    public string Type { get; set; }
    [XmlAttribute("Include")]
    public string Include { get; set; }
}

public class Item
{
    [XmlAttribute("Name")]
    public string Name { get; set; }
    [XmlElement("Artifact")]
    public List<Artifact> Artifacts { get; set; }
}

public class Artifact
{
    [XmlAttribute("Kind")]
    public int Kind { get; set; }
    [XmlAttribute("Action")]
    public int Action { get; set; }
}

序列化:

Product p = new Product()
{
    Cycle = new Cycle() { Type = "x0446" },
    Brand = new Brand() { Type = "z773g", Include = "All" },
    Updates = new List<Item>()
    {
        new Item() { Name = "Foo", 
                     Artifacts = new List<Artifact>() {
                        new Artifact() { Action = 3, Kind = 6 }
                    }
        },
        new Item() { Name = "Bar", 
                     Artifacts = new List<Artifact>() {
                        new Artifact() { Action = 3, Kind = 6 },
                        new Artifact() { Action = 3, Kind = 53 },
                    }
        }
    }
};

XmlSerializer serializer = new XmlSerializer(typeof(Product));
Stream stream = new MemoryStream(); // use whatever you need
serializer.Serialize(stream, p);

结果:

<Product>
    <Cycle Type = "x0446" />
    <Brand Type = "z773g" Include="All" />
    <Updates>
        <Item Name = "Foo">
            <Artifact Kind="6" Action="3" />
        </Item>
        <Item Name = "Bar">
            <Artifact Kind="6" Action="3" />
            <Artifact Kind="53" Action="3" />
        </Item>
    </Updates>
</Product>

答案 2 :(得分:0)

这里有一些代码(错过了一个属性)

using System;
using System.Xml;
using System.Xml.Serialization;
using System.Collections.Generic;

[Serializable]
[XmlRoot("Product")]
public class Product
{
    [XmlElement("Cycle")]
    public Cycle Cycle { get; set; }

    [XmlElement("Updates")]
    public Updates Updates { get; set; }

    public Product()
    {
        Cycle = new Cycle();
        Updates = new Updates();
    }
}

[Serializable]
public class Cycle
{
    [XmlAttribute("Type")]
    public string Type { get; set; }
}

[Serializable]
public class Updates
{
    [XmlElement("Item")]
    public List<Item> Items { get; set; }

    public Updates()
    {
        Items = new List<Item>();
    }
}

[Serializable]
public class Item
{
    [XmlElement("Artifact", typeof(Artifact))]
    public List<Artifact> Artifacts { get; set; }

    public Item()
    {
        Artifacts = new List<Artifact>();
    }
}

[Serializable]
public class Artifact
{
    [XmlAttribute("Kind")]
    public int Kind { get; set; }
}

这里是序列化的代码

using System;
using System.Xml;
using System.Xml.Serialization;
using System.Collections.Generic;
using System.IO;
using System.Text;

    private static string SerializeMe(object o)
    {
        XmlSerializer s = new XmlSerializer(o.GetType());

        MemoryStream stream = new MemoryStream();

        XmlWriter writer = new XmlTextWriter(stream, Encoding.Default);

        s.Serialize(writer, o);

        stream.Flush();

        stream.Seek(0, SeekOrigin.Begin);

        return Encoding.Default.GetString(stream.ToArray());
    }

现在这里是控制台上的测试代码

    static void Main(string[] args)
    {
        Product p = new Product();

        p.Cycle.Type = "whatever";

        Item i = new Item();
        i.Artifacts.Add(new Artifact{Kind = 45});

        p.Updates.Items.Add(i);

        Console.WriteLine(SerializeMe(p));

        Console.ReadLine();
    }

希望这会有所帮助:)

答案 3 :(得分:0)

如果您有这种结构的XML架构(或可以生成一个) - 我的首选是使用XSD.exe生成该类。