Использование декораций XML для определения значений по умолчанию во время десериализации - PullRequest
15 голосов
/ 16 августа 2010

У меня проблема с десериализацией некоторых XML; XML, предоставленный третьей стороной, довольно многословен, поэтому, если для определенного элемента не задано значение, он предоставит и пустой элемент (например, <element1 />).

Это проблема для определенных элементов, например, тех, которые предназначены для хранения целых чисел. У меня есть контроль над третьей стороной, поэтому я могу либо заставить их указать значение по умолчанию (<myinteger>0</myinteger>), либо я могу заставить их полностью пропустить эти элементы. Оба из них должны избежать проблемы.

Однако в будущем могут возникнуть ситуации, когда у нас не будет такого большого контроля - в каком случае есть способ указать, возможно, посредством украшения, значение по умолчанию?

    [XmlElement("myinteger")=0???]
    public int MyInteger
    {
        get
        {
            return myInteger;
        }
        set
        {
            myInteger= value;
        }
    }

Ответы [ 2 ]

37 голосов
/ 16 августа 2010

XmlSerializer поддерживает [DefaultValue], но использует его во время сериализации .Во время десериализации он просто запускает конструктор, затем принимает входящие значения и применяет их.Таким образом, общий подход заключается в использовании конструктора (или инициализаторов полей):

public Foo() {
    Bar = 4;
}
[DefaultValue(4), XmlAttribute("bar")]
public int Bar {get;set;}

Однако ;XmlSerializer интерпретирует это не как «предоставить пустой элемент», а скорее как «опустить элемент (/ attribute)».Даже int? не отображается на "пусто".Чтобы обрабатывать пустых элементов, вы должны обрабатывать его как строку.Что некрасиво.

0 голосов
/ 31 октября 2012

Оформление с использованием [DefaultValue] не кажется полным решением, так как оно не всегда работает. Другое простое решение (может быть не чистым)

public string _sourceSubFolderName;
    [DefaultValueAttribute("")]
    [XmlElement("SourceSubFolderName")]
    public string SourceSubFolderName
    {
        get { return string.IsNullOrEmpty(_sourceSubFolderName) ? 
               string.Empty : _sourceSubFolderName; }
        set { _sourceSubFolderName = value; }
    }
...