2016-04-01 6 views
0

einige Schwierigkeiten Deserialisieren das folgende XML zu einem Objekt in dem effizientesten/sauberste Weg zu haben:Deserialize Schlüssel/Wert-xml in ein Objekt

<item xsi:type="ns2:Map" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> 
    <item> 
     <key xsi:type="xsd:string">mailinglistid</key> 
     <value xsi:type="xsd:string">1</value> 
    </item> 
    <item> 
     <key xsi:type="xsd:string">uniqueid</key> 
     <value xsi:type="xsd:string">1a0d0d2195</value> 
    </item> 
    <item> 
     <key xsi:type="xsd:string">name</key> 
     <value xsi:type="xsd:string">OSM NL</value> 
    </item> 
</item> 

Dies ist ein einzelne Element zusammen mit seinen Eigenschaften. Wie Sie sehen können, sind die Eigenschaften als Schlüssel/Wert-Paare definiert.

Weil sie Schlüsselwertepaare ich kann nicht einen Weg finden, um die XML-deserialize Attribute zu verwenden (wie in dieser Frage beschrieben: How to deserialize xml to object)

Deshalb habe ich die folgende Alternative geschaffen:

// Retrieves all the elements from the "return" node in the Mailinglist_allResponse node. 
var items = response.ResponseFromServer.Descendants(_engineResponseNamespace + "Mailinglist_allResponse").Descendants("return").Elements(); 

foreach (var item in items) 
{ 
    var values = item.Descendants("item").ToArray(); 

    var list = new EngineMailingList 
    { 
     MailingListId = 
      values.Descendants("key") 
       .First(v => v.Value == "mailinglistid") 
       .ElementsAfterSelf("value") 
       .First() 
       .Value, 
     UniqueId = 
      values.Descendants("key") 
       .First(v => v.Value == "uniqueid") 
       .ElementsAfterSelf("value") 
       .First() 
       .Value, 
     Name = 
      values.Descendants("key") 
       .First(v => v.Value == "name") 
       .ElementsAfterSelf("value") 
       .First() 
       .Value, 
    }; 

    result.Add(list); 

Wie Sie sehen, ist dies viel mehr Code als bei Verwendung der Deserialize-Attribute. Gibt es eine Möglichkeit, wie ich diese Attribute noch verwenden könnte, damit mein Code sauberer/effizienter sein könnte? Ich werde viel von diesen Funktionen anders machen müssen.

+0

Das XML sieht ungültig. Es sollte Namespaces geben, die den Namespacepräfixen 'ns' und' xsd' von 'xsi: type =" ns2: Map "' und 'xsi: type =" xsd: string "' entsprechen. Das ['xsi: type'] (https://www.w3.org/TR/xmlschema-1/#xsi_type) Attribut ist eine Standardmethode, um den Typ eines polymorphen Elements anzugeben, siehe [Xsi: type Attribut Binding Support ] (https://msdn.microsoft.com/en-us/library/ca1ks327.aspx). – dbc

+0

Entschuldigung, das XML in der Post ist nur ein Teil davon. Es hat die Namespaces in der Spitze, ich habe gerade entschieden, sie nicht in diesen Beitrag aufzunehmen. –

+0

@Jurgen Welschen können Sie uns die Namespaces zeigen, die Sie nicht enthalten .... – Monty

Antwort

1

Ich glaube nicht, dass Attribute wegen der Schlüssel/Wert-Struktur arbeiten werden. Es gibt keine Möglichkeit für ein Programm, aus dem XML allein abzuleiten, welche Eigenschaften ein Objekt hat. Ich würde eine statische Erweiterungsmethode Helferfunktion machen die Werte zu erhalten:

public static string GetValue(this XElement element, string key){ 
     return values.Descendants("key") 
        .First(v => v.Value == key) 
        .ElementsAfterSelf("value") 
        .First() 
        .Value; 
    } 

Auf diese Weise Ihren Code wie folgt aussehen könnte:

MailingListId = values.GetValue("mailinglistid"), 
UniqueId = values.GetValue("uniqueid"), 
Name = values.GetValue("name") 
+0

Ok danke! also keine echte Möglichkeit, dies mit Deserialisierungsattributen zu tun. Die Hilfsfunktion ist eine gute Idee! –

+0

Sie können möglicherweise Ihr eigenes benutzerdefiniertes Attribut dafür erstellen, aber es könnte mehr Ärger geben, als es wert ist – jle

Verwandte Themen