簡體   English   中英

XmlSerializer System.InvalidOperationException

[英]XmlSerializer System.InvalidOperationException

我的應用程序中包含以下代碼:

[Serializable]
public class Class
{
    private string name = "";
    private List<Property> property = new List<Property>();
    [XmlAttribute]
    public string Name
    {
        get { return name; }
        set { name = value; }
    }
    [XmlArray(ElementName = "Properties")]
    public List<Property> Property
    {
        get { return property; }
        set { property = value; }
    }
    public Class() { }
}
[Serializable]
public class Property
{
    private string name = "";
    private object value;

    [XmlAttribute]
    public string Name
    {
        get { return name; }
        set { name = value; }
    }
    [XmlElement]
    public object Value
    {
        get { return this.value; }
        set { this.value = value; }
    }
    public Property() { }
}
class Program
{
    static void Main(string[] args)
    {
        List<Class> classList = GetClassList();
        SerializeConfig("test.xml", classList);
    }
    private static List<Class> GetClassList()
    {
        return new List<Class>(){
            new Class()
            {
                Name = "MyFirstClass",
                Property = new List<Property>() {
                    new Property(){ Name = "StringProperty",    Value = "Simple1"},
                    new Property(){ Name = "IntProperty",       Value = 3},
                    new Property(){ Name = "DoubleProperty",    Value = 5.5},
                    new Property(){ Name = "ListProperty",      Value = new List<int>(){
                        1,2,3,4,5
                        }
                    },
                }
            }
        };
    }
    public static List<Class> DeserializeConfig(string configPath)
    {
        if (!File.Exists(configPath)) return null;
        try
        {
            XmlSerializer serializer = new XmlSerializer(typeof(List<Class>), new XmlRootAttribute("Classes"));
            using (FileStream fs = File.Open(configPath, FileMode.Open))
            {
                return (List<Class>)serializer.Deserialize(fs);
            }
        }
        catch (Exception)
        {
            return null;
        }
    }
    public static bool SerializeConfig(string path, List<Class> config)
    {
        try
        {
            XmlSerializer serializer = new XmlSerializer(typeof(List<Class>), new XmlRootAttribute("Classes"));
            using (FileStream fs = File.Open(path, FileMode.Create))
            {
                serializer.Serialize(fs, config);
            }
        }
        catch (Exception)
        {
            return false;
        }
        return true;
    }
}

如果運行此代碼,則將獲得System.InvalidOperationException及其以下消息:

{System.InvalidOperationException: There was an error generating the XML document. ---> System.InvalidOperationException: The type System.Collections.Generic.List`1[[System.Int32, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]] may not be used in this context.
   at System.Xml.Serialization.XmlSerializationWriter.WriteTypedPrimitive(String name, String ns, Object o, Boolean xsiType)
   at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriterList1.Write1_Object(String n, String ns, Object o, Boolean isNullable, Boolean needType)
   at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriterList1.Write2_Property(String n, String ns, Property o, Boolean isNullable, Boolean needType)
   at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriterList1.Write3_Class(String n, String ns, Class o, Boolean isNullable, Boolean needType)
   at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriterList1.Write4_Classes(Object o)
   --- End of inner exception stack trace ---
   at System.Xml.Serialization.XmlSerializer.Serialize(XmlWriter xmlWriter, Object o, XmlSerializerNamespaces namespaces, String encodingStyle, String id)
   at System.Xml.Serialization.XmlSerializer.Serialize(Stream stream, Object o, XmlSerializerNamespaces namespaces)
   at System.Xml.Serialization.XmlSerializer.Serialize(Stream stream, Object o)
   at SerializeTest.Program.SerializeConfig(String path, List`1 config) in [...]\Program.cs:line 102}

為什么我不能以這種方式序列化列表? 我如何建立解決方法?

好的,我找到了解決方案。 我必須添加自定義類型。

XmlSerializer serializer = new XmlSerializer(typeof(List<Class>), null, new Type[] { typeof(List<int>) }, new XmlRootAttribute("Classes"),"");

因此,我必須從列表中收集所有類型:

private static Type[] CollectTypesFromCollection(List<Class> collection)
{
    List<Type> types = new List<Type>();
    foreach (Class item in collection)
        foreach (Property property in item.Property)
            if (!types.Contains(property.Value.GetType()))
                types.Add(property.Value.GetType());
    return types.ToArray();
}

並可以像這樣使用序列化器:

XmlSerializer serializer = new XmlSerializer(typeof(List<Class>),null,CollectTypesFromCollection(config), new XmlRootAttribute("Classes"),"");

我建議您在進入XML Serialization之前先進行一下了解,在XML Serialization中,由於創建List的方式而導致錯誤。

XML序列化簡介

參考: XmlSerializer列表項元素名稱

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM