Как XML сериализовать тип - PullRequest
       13

Как XML сериализовать тип

12 голосов
/ 14 ноября 2008

Как мне сериализовать 'Type'?

Я хочу сериализовать в XML объект, который имеет свойство, являющееся типом объекта. Идея состоит в том, что после десериализации я могу создать объект этого типа.

public class NewObject
{
}

[XmlRoot]
public class XmlData
{
    private Type t;

    public Type T
    {
        get { return t; }
        set { t = value; }
    }
}
    static void Main(string[] args)
    {
        XmlData data = new XmlData();
        data.T = typeof(NewObject);
        try
        {
            XmlSerializer serializer = new XmlSerializer(typeof(XmlData));
            try
            {
                using (FileStream fs = new FileStream("test.xml", FileMode.Create))
                {
                    serializer.Serialize(fs, data);
                }
            }
            catch (Exception ex)
            {

            }
        }
        catch (Exception ex)
        {

        }
    }

Я получаю это исключение: «Тип ConsoleApplication1.NewObject не ожидался. Используйте атрибут XmlInclude или SoapInclude для указания типов, которые статически не известны.»

Куда мне положить [XmlInclude]? Это вообще возможно?

Ответы [ 6 ]

18 голосов
/ 06 июля 2011
Класс

Type не может быть сериализован, потому что System.RuntimeType недоступен для нашего кода, это внутренний тип CLR. Вы можете обойти это, используя вместо этого имя типа, например:

public class c 
{       
    [XmlIgnore]
    private Type t;
    [XmlIgnore]
    public Type T {
        get { return t; }
        set { 
                t = value;
                tName = value.AssemblyQualifiedName;
            }
    }

    public string tName{
        get { return t.AssemblyQualifiedName; }
        set { t = Type.GetType(value);}
    }
}
3 голосов
/ 30 апреля 2009

Сериализация XML сериализует только открытые поля и значения свойств объекта в поток XML. Сериализация XML не включает информацию о типе. Например, если у вас есть объект Book, который существует в пространстве имен библиотеки, нет гарантии, что он будет десериализован в объект того же типа.

Источник: MSDN: введение в сериализацию XML

3 голосов
/ 14 ноября 2008

В итоге я преобразовал имя типа в строку, чтобы сохранить его в XML.

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

3 голосов
/ 14 ноября 2008

Вы могли бы потенциально реализовать интерфейс IXmlSerializable и использовать Type.FullName (вам также может понадобиться Type.AssemblyQualifiedName) для сериализации и Assembly.GetType(string) для десериализации вашего элемента типа.

1 голос
/ 24 января 2011

Ужасно, но это работает. Создайте класс, который включает тип объекта и сериализованную строку.

ех

Class dummie
{
    Type objType;
    string xml;
}
1 голос
/ 16 ноября 2008

Проблема в том, что тип XmlData.T на самом деле "System.RuntimeType" (подкласс типа), который, к сожалению, не является общедоступным. Это означает, что нет никакого способа сообщить сериализации, какие типы ожидать. Я предлагаю только сериализовать имя типа или полностью определенное имя, как предлагает Джей Базузи.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...