C# 序列化接口

C# 序列化接口,c#,xml-serialization,C#,Xml Serialization,我正在尝试运行类似以下内容的代码: using System; using System.Collections.Generic; using System.IO; using System.Xml.Serialization; namespace ConsoleApplication1 { [Serializable] [XmlInclude(typeof(List<Class2>))] public class Class1 {

我正在尝试运行类似以下内容的代码:

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

namespace ConsoleApplication1
{
    [Serializable]
    [XmlInclude(typeof(List<Class2>))]
    public class Class1
    {
        private IList<Class2> myArray;

        public IList<Class2> MyArray
        {
            get { return myArray; }
            set { myArray = value; }
        }

    }

    public class Class2
    {
        private int myVar;

        public int MyProperty
        {
            get { return myVar; }
            set { myVar = value; }
        }

    }

    class Program
    {
        static void Main(string[] args)
        {
            XmlSerializer ser = new XmlSerializer(typeof(Class1), new Type[] { typeof(List<Class2>) });
            FileStream stream = File.OpenWrite("Data.xml");
            ser.Serialize(stream, new List<Class1>());
            stream.Close();
        }
    }
}
使用系统;
使用System.Collections.Generic;
使用System.IO;
使用System.Xml.Serialization;
命名空间控制台应用程序1
{
[可序列化]
[xmlclude(typeof(List))]
公共班级1
{
私有IList myArray;
公共IList MyArray
{
获取{return myArray;}
设置{myArray=value;}
}
}
公共课2
{
私有int-myVar;
公共财产
{
获取{return myVar;}
设置{myVar=value;}
}
}
班级计划
{
静态void Main(字符串[]参数)
{
XmlSerializer ser=newXmlSerializer(typeof(Class1),new Type[]{typeof(List)});
FileStream-stream=File.OpenWrite(“Data.xml”);
序列化(流,新列表());
stream.Close();
}
}
}
谁能解释一下我做错了什么

我得到一个:

无法序列化成员。。我的数组。。。因为它是一个接口


XmlInclude不应该解决这个问题吗?

不。不能序列化接口。曾经它刚刚告诉你了

接口只不过是一组行为的描述。它没有说明实例的内容。特别是,尽管实现接口的类的实例必须实现其所有成员,但它肯定有自己的属性,需要序列化

它将如何反序列化

在另一端,将使用哪个类来反序列化接口

您包括了typeof(List),但MyArray的类型是IList,它本身并不是明显的数据结构,而更像是一个占位符,用来表示某种数据结构

将MyArray的类型更改为特定类型(例如,as List),它应该可以工作

    private List<Class2> myArray;

    public List<Class2> MyArray
    {
        get { return myArray; }
        set { myArray = value; }
    }
私有列表myArray;
公共列表MyArray
{
获取{return myArray;}
设置{myArray=value;}
}

以下是我原则上倾向于使用的未经测试的阴暗变通方法:

private IList<Class2> myArray;
[XmlIgnore]
public IList<Class2> MyArray
{
    get { return myArray; }
    set { myArray = value; }
}

[XmlElement("MyArray")]
public object MyArraySerializable
{
    get { return MyArray; }
    set { MyArray = value as IList<Class2>; }
}
私有IList myArray;
[XmlIgnore]
公共IList MyArray
{
获取{return myArray;}
设置{myArray=value;}
}
[XmlElement(“MyArray”)]
公共对象MyArraySriable
{
获取{return MyArray;}
将{MyArray=value设置为IList;}
}
这将序列化您可能用作泛型对象的任何列表,该列表带有一个type属性,该属性将告诉反序列化程序对象的实际类型,因此当该对象被反序列化时,应该再次将其转换为
IList
。记住提供接口可能采用的任何类型


我看不出任何序列化程序无法序列化此类属性的原因。这并不是说您实际上试图序列化一个接口,而是试图序列化一个实现某个接口的对象(这与抽象子类化没有太大区别,有些编程语言甚至只对接口进行操作)

当序列化程序应该序列化该对象时,它知道该对象实现了该接口,它真正需要做的就是序列化它并附加type属性(就像序列化抽象类或一般的超类一样)


现在,反序列化程序查看该类型,并可以检查该对象是否确实实现了所需的接口,然后将其反序列化为相应的属性。

或者改用。

@Shahar:yes。不要那样做。使用具体的类型,而不是接口。它将如何反序列化?作为序列化的类的实例,与List相同。在另一端,将使用哪个类来反序列化接口?请看第一个答案。但另一方如何知道哪个类被序列化了呢?它会知道是哪一类吗?@JohnSaunders,你第一段说的“你做不到”是对的。你所说的一切都是为了证明为什么会是这样。这些理由都是假的。获取一个接口,并用一个没有成员的抽象类替换它。这根本不会改变代码的工作方式。突然你可以序列化它了!此外,你在上面的评论中确实说过“不要那样做”。这确实是正确的答案。阿门。在这个问题上,序列化程序是愚蠢的!谢谢你的帮忙。使用接口要好得多,因为继承仅限于一个基类。谁说过反序列化?