Ricevo un xml dal terzo utente e devo deserializzare nell'oggetto C#. Questo xml può contenere attributi con valore di tipo intero o valore vuoto: attr = "11" o attr = "". Voglio deserializzare questo valore di attributo nella proprietà con il tipo di numero nullable intero. Ma XmlSerializer non supporta la deserializzazione in tipi nullable. Il seguente codice di test non riesce durante la creazione di XmlSerializer con InvalidOperationException {"Si è verificato un errore che riflette il tipo 'TestConsoleApplication.SerializeMe'."}.Deserializzazione del valore dell'attributo xml vuoto nella proprietà int nullo utilizzando XmlSerializer
[XmlRoot("root")]
public class SerializeMe
{
[XmlElement("element")]
public Element Element { get; set; }
}
public class Element
{
[XmlAttribute("attr")]
public int? Value { get; set; }
}
class Program {
static void Main(string[] args) {
string xml = "<root><element attr=''>valE</element></root>";
var deserializer = new XmlSerializer(typeof(SerializeMe));
Stream xmlStream = new MemoryStream(Encoding.ASCII.GetBytes(xml));
var result = (SerializeMe)deserializer.Deserialize(xmlStream);
}
}
Quando cambio tipo di proprietà 'Valore' a int, deserializzazione non riesce con InvalidOperationException:
C'è un errore nel documento XML (1, 16).
Qualcuno può consigliare come deserializzare attributo con valore vuoto in tipo annullabile (come null) Allo stesso tempo deserializzazione valore di attributo non vuota in un numero intero? C'è qualche trucco per questo, quindi non dovrò fare manualmente la deserializzazione di ogni campo (in realtà ce ne sono molti)?
Aggiornamento dopo il commento da ahsteele:
-
Per quanto ne so, questo attributo funziona solo con XmlElementAttribute - Questo attributo specifica che l'elemento non ha contenuto, se gli elementi figlio o corpo testo. Ma ho bisogno di trovare la soluzione per XmlAttributeAttribute. Ad ogni modo non posso cambiare xml perché non ne ho il controllo.
-
Questa proprietà funziona solo quando il valore di attributo non è vuoto o quando l'attributo è mancante. Quando attr ha valore vuoto (attr = '') il costruttore di XmlSerializer fallisce (come previsto).
public class Element { [XmlAttribute("attr")] public int Value { get; set; } [XmlIgnore] public bool ValueSpecified; }
Custom Nullable class like in this blog post by Alex Scordellis
ho cercato di adottare la classe da questo post del blog al mio problema:
[XmlAttribute("attr")] public NullableInt Value { get; set; }
Ma XmlSerializer costruttore fallisce con InvalidOperationException:
Non può serializzare membro 'Valore' di tipo TestConsoleApplication.NullableInt.
XmlAttribute/XmlText non può essere usato per codificare i tipi di applicazione IXmlSerializable}
soluzione surrogato Ugly (mannaggia a me che ho scritto questo codice qui :)):
public class Element { [XmlAttribute("attr")] public string SetValue { get; set; } public int? GetValue() { if (string.IsNullOrEmpty(SetValue) || SetValue.Trim().Length <= 0) return null; int result; if (int.TryParse(SetValue, out result)) return result; return null; } }
Ma don Voglio inventare la soluzione in questo modo perché rompe l'interfaccia della mia classe per i suoi consumatori. Sarebbe meglio implementare manualmente l'interfaccia IXmlSerializable.
Attualmente sembra che devo implementare IXmlSerializable per tutta la classe Element (è grande) e non ci sono semplici soluzione ...
Il "Uso XmlSerializer per deserializzare in un Nullable" collegamento è guasto . [Ecco una versione cache di google] (http://webcache.googleusercontent.com/search?q=cache:vT5GiyOCWyIJ:www.rqna.net/qna/zzrzt-deserialise-missing-xml-attribute-to-nullable-type .html) – Anttu
@Anttu Ho cambiato il link nella risposta all'archivio Wayback Machine dell'originale * Usando XmlSerializer per deserializzare in un Nullable *. –
ahsteele