XML сериализация List<IFigure>

370
25 мая 2017, 07:28

Доброго времени суток. Необходимо сериализовать список фигур, реализующих общий интерфейс IFigure. Код сериализации:

        XmlSerializer f = new XmlSerializer(typeof(List<IFigure>));
        FileStream fs = new FileStream("figures.xml", FileMode.Create);
        try {
            f.Serialize(fs, figures);
        }
        catch (SerializationException ex) {
            MessageBox.Show(ex.Message);
        }
        finally {
            fs.Close();
        }

При попытке сериализовать список List возникли проблемы:

An unhandled exception of type 'System.NotSupportedException' occurred in System.Xml.dll

Additional information: Невозможно сериализовать интерфейс lab7_XML.IFigure.

Есть интерфейс:

public interface IFigure {
    double Area { get; }
    double this[int i] { get; }
    String coord();
    String Color { get; }
    String ADD { get; }
}

Его реализуют 2 класса, класс Circle:

[Serializable]
public class Circle : IFigure {
    public double[] coordXY;
    public string color;
    public Circle() { }
    public Circle(double[] coord, string color) {
        this.color = color;
        coordXY = new double[coord.Length];
        Array.Copy(coord, coordXY, coord.Length);
    }
}

И класс Rect:

[Serializable]
public class Rect : IFigure {
    public double[] coordXY;
    public string color;
    public Rect() { }
    public Rect(double[] coord, string color) {
        this.color = color;
        if (coord.Length > 8) throw new Exception("Слишком много вершин!");
        coordXY = new double[coord.Length];
        Array.Copy(coord, coordXY, coord.Length);
    }
}

С сериализацией списков обычных объектов у меня проблем не возникало. Подскажите, пожалуйста, в каком направлении двигаться. Спасибо.

Answer 1

Используйте список объектов абстрактного типа, вместо интерфейса.

Пометьте атрибутом [XmlInclude(typeof(DerivedClass))] все дочерние классы, которые хотите сериализовать:

[XmlInclude(typeof(Circle))]
[XmlInclude(typeof(Rect))]
public abstract class Figure 
{
    //ваши свойства из интерфейса IFigure
}
[Serializable]
public class Circle : Figure
{    
}
[Serializable]
public class Rect : Figure
{
}

поменять:

XmlSerializer f = new XmlSerializer(typeof(List<IFigure>));

на:

XmlSerializer f = new XmlSerializer(typeof(List<Figure>));
READ ALSO
Реализация AES режима шифрования CBC на основе ECB в C#

Реализация AES режима шифрования CBC на основе ECB в C#

Здравствуйте! Нужно реализовать на основе ECB (собственно, без использования библиотеки Cryptography для CBC) шифрование в режиме CBC (для алгоритма...

476
Ошибка с интерполяцией

Ошибка с интерполяцией

Здравствуйте, В проекте таких записей у меня очень много

204
Работа с WiFi на C#

Работа с WiFi на C#

День добрый! Суть моего вопроса заключается в следующем: возможно ли, используя C#, работать с WiFi, то есть получать список доступных сетей,...

591
Поиск файла из ListBox

Поиск файла из ListBox

Есть ListBox в который добавляются файлы через OpenFileDialogКак по нажатию на Button найти информацию в интернете о выбранной строке в ListBox? То есть пользователь...

262