Benutzer mit den meisten Antworten
LINQ XML Parent/Child nodes auslesen

Frage
-
Hallo,
Ich suche im moment eine lösung um aus einer XML datei die Parent/child Nodes so auszulesen das ich sie mit der verbindung zum Parent/child habe.
So ansich auslesen kann ich die Parent/Child nodes.
Meine XML sieht so aus:
<Auftrag> <Nummer>7486234156</Nummer> <Bearbeiter>Maximilian</Bearbeiter> <auftragsnr>2012-852368</auftragsnr> <letztebearbeitung>09.05.2012 08:00:00</letztebearbeitung> <Projekt> <PName>Projekt Swordfischi</PName> <Nummer>75321458</Nummer> <adresse> <plz>11111</plz> <ortsname>Berlin</ortsname> <ortsteil>Kreuzberg</ortsteil> <strasse>Heinrichstr</strasse> <hausNr>49</hausNr> </adresse> <Auftraggeber>359DDS376A</Auftraggeber> </Projekt> <Projektbetreiber> <Name>Weihnachtsmann GmbH</Name> <adresse> <plz>11112</plz> <ortsname>Frankfurt</ortsname> <ortsteil>Mitte</ortsteil> <strasse>Hagbutta</strasse> <hausnr>23</hausnr> </adresse> <Partnernummer>554</Partnernummer> </Projektbetreiber> <termin> <terminVon>20.05.2012 08:00:00</terminVon> <alternativtermin></alternativtermin> </termin> <Auftragsbeschreibung> <uAuftragsbeschreibung> <Gruppe>Installation</Gruppe> <Nr>1</Nr> <auftragsbs>Installation H882/E 12</auftragsbs> </uAuftragsbeschreibung> <uAuftragsbeschreibung> <Gruppe>Installation</Gruppe> <Nr>2</Nr> <auftragsbs>Einrichtung H882/E 12</auftragsbs> </uAuftragsbeschreibung> </Auftragsbeschreibung> </Auftrag>
Mein C# Code :
// VARIANTE 1 XDocument xmlDoc2 = XDocument.Load("c:\\a.xml"); var nodeNames = xmlDoc2.Root.Descendants() .Select(eh => eh.Name.LocalName) .Distinct() .ToList(); listBox1.Items.AddRange(nodeNames.ToArray()); // VARIANTE 2 XDocument xmlDoc2 = XDocument.Load("c:\\a.xml"); IEnumerable<XNode> dnas = from node in xmlDoc2.DescendantNodes() select node; foreach (XNode node in dnas) { if (node is XElement) textBox1.Text = textBox1.Text + "\r\n"+ (node as XElement).Name; //Console.WriteLine((node as XElement).Name); else textBox1.Text = textBox1.Text; //Console.WriteLine(node); }
Und so ist das ergebniss was ich erhalte bei beiden. Ohne die //---"" natürlich.
Auftrag Nummer Bearbeiter auftragsnr letztebearbeitung Projekt //--> CHILDNODE PName Nummer adresse //----GRANDCHILDNODE plz ortsname ortsteil strasse hausNr //-----------GRANDCHILDNODEENDE Auftraggeber //-----------CHILDNODEENDE Projektbetreiber //--> CHILDNODE Name adresse //----GRANDCHILDNODE plz ortsname ortsteil strasse hausnr //-----------GRANDCHILDNODEENDE Partnernummer //-----------CHILDNODEENDE termin //--> CHILDNODE terminVon alternativtermin //-----------CHILDNODEENDE Auftragsbeschreibung //--> CHILDNODE uAuftragsbeschreibung //----GRANDCHILDNODE Installation Nr auftragsbs //-----------CHILDNODEENDE Auftragsbeschreibung //--> CHILDNODE uAuftragsbeschreibung //----GRANDCHILDNODE Installation Nr auftragsbs //-----------CHILDNODEENDE // ENDE XML
Was ich aber gerne hätte wie es ausschauen soll ist:
Auftrag Nummer Bearbeiter auftragsnr letztebearbeitung //Projekt //--> CHILDNODE Projekt.PName Projekt.Nummer Projekt.adresse //----GRANDCHILDNODE Projekt.adresse.plz Projekt.adresse.ortsname Projekt.adresse.ortsteil Projekt.adresse.strasse Projekt.adresse.hausNr Projekt.Auftraggeber //Projektbetreiber //--> CHILDNODE Projektbetreiber.Name //Projektbetreiber.adresse //----GRANDCHILDNODE Projektbetreiber.adresse.plz Projektbetreiber.adresse.ortsname Projektbetreiber.adresse.ortsteil Projektbetreiber.adresse.strasse Projektbetreiber.adresse.hausnr Projektbetreiber.Partnernummer //termin //--> CHILDNODE termin.terminVon termin.alternativtermin //Auftragsbeschreibung //--> CHILDNODE Auftragsbeschreibung.uAuftragsbeschreibung Auftragsbeschreibung.uAuftragsbeschreibung.Installation Auftragsbeschreibung.uAuftragsbeschreibung.Nr Auftragsbeschreibung.uAuftragsbeschreibung.auftragsbs //Auftragsbeschreibung //--> CHILDNODE Auftragsbeschreibung.uAuftragsbeschreibung Auftragsbeschreibung.uAuftragsbeschreibung.Installation Auftragsbeschreibung.uAuftragsbeschreibung.Nr Auftragsbeschreibung.uAuftragsbeschreibung.auftragsbs // ENDE XML
Grund ist. Die Grandchild/Child elemente die selben namen sollen unterschiedlich bearbeitet werden. Ich bin gerade dabei IF verschachtelungen zu schreiben der überprüft ob die elemente vorhanden sind und dann bearbeitet. Aber dachte mir wäre doch schöner wenn ich das so direkt auslesen kann und dann weiterbearbeiten. Weil die XML datein haben zwar alle die selbe struktur, aber nicht immer gleich viele Childs/Grandchilds....
Antworten
-
So ganz konsistent erscheint mir dein gewünschtes Ergebnis nicht, so ist mir nicht klar, warum nicht "Auftrag" als Wurzelelement jeweils bei den Namen vorangestellt wird . Deshalb hier erst mal ein Beispiel, das folgendes ausgibt:
Auftrag Auftrag.Nummer Auftrag.Bearbeiter Auftrag.auftragsnr Auftrag.letztebearbeitung Auftrag.Projekt Auftrag.Projekt.PName Auftrag.Projekt.Nummer Auftrag.Projekt.adresse Auftrag.Projekt.adresse.plz Auftrag.Projekt.adresse.ortsname Auftrag.Projekt.adresse.ortsteil Auftrag.Projekt.adresse.strasse Auftrag.Projekt.adresse.hausNr Auftrag.Projekt.Auftraggeber Auftrag.Projektbetreiber Auftrag.Projektbetreiber.Name Auftrag.Projektbetreiber.adresse Auftrag.Projektbetreiber.adresse.plz Auftrag.Projektbetreiber.adresse.ortsname Auftrag.Projektbetreiber.adresse.ortsteil Auftrag.Projektbetreiber.adresse.strasse Auftrag.Projektbetreiber.adresse.hausnr Auftrag.Projektbetreiber.Partnernummer Auftrag.termin Auftrag.termin.terminVon Auftrag.termin.alternativtermin Auftrag.Auftragsbeschreibung Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.Gruppe Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.Nr Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.auftragsbs Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.Gruppe Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.Nr Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.auftragsbs
XDocument doc = XDocument.Load("input.xml"); List<string> names = doc.Descendants().Select(el => string.Join(".", el.AncestorsAndSelf().InDocumentOrder().Select(anc => anc.Name.LocalName).ToArray())).ToList(); foreach (string name in names) { Console.WriteLine(name); }
So du das das vorangestellte "Auftrag" nicht willst, dann eventuell per
List<string> names = doc.Descendants().Select(el => string.Join(".", el.AncestorsAndSelf().InDocumentOrder().Skip(1).Select(anc => anc.Name.LocalName).ToArray())).ToList();
ansonsten musst du die Kriterien, nach denen die Namen zusammengefügt werden sollen, noch mal genauer erklären, so du mit den Vorschlägen das nicht selbst anpassen kannst.
MVP Data Platform Development My blog
- Als Antwort markiert mtotm Freitag, 18. Mai 2012 17:20
Alle Antworten
-
So ganz konsistent erscheint mir dein gewünschtes Ergebnis nicht, so ist mir nicht klar, warum nicht "Auftrag" als Wurzelelement jeweils bei den Namen vorangestellt wird . Deshalb hier erst mal ein Beispiel, das folgendes ausgibt:
Auftrag Auftrag.Nummer Auftrag.Bearbeiter Auftrag.auftragsnr Auftrag.letztebearbeitung Auftrag.Projekt Auftrag.Projekt.PName Auftrag.Projekt.Nummer Auftrag.Projekt.adresse Auftrag.Projekt.adresse.plz Auftrag.Projekt.adresse.ortsname Auftrag.Projekt.adresse.ortsteil Auftrag.Projekt.adresse.strasse Auftrag.Projekt.adresse.hausNr Auftrag.Projekt.Auftraggeber Auftrag.Projektbetreiber Auftrag.Projektbetreiber.Name Auftrag.Projektbetreiber.adresse Auftrag.Projektbetreiber.adresse.plz Auftrag.Projektbetreiber.adresse.ortsname Auftrag.Projektbetreiber.adresse.ortsteil Auftrag.Projektbetreiber.adresse.strasse Auftrag.Projektbetreiber.adresse.hausnr Auftrag.Projektbetreiber.Partnernummer Auftrag.termin Auftrag.termin.terminVon Auftrag.termin.alternativtermin Auftrag.Auftragsbeschreibung Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.Gruppe Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.Nr Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.auftragsbs Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.Gruppe Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.Nr Auftrag.Auftragsbeschreibung.uAuftragsbeschreibung.auftragsbs
XDocument doc = XDocument.Load("input.xml"); List<string> names = doc.Descendants().Select(el => string.Join(".", el.AncestorsAndSelf().InDocumentOrder().Select(anc => anc.Name.LocalName).ToArray())).ToList(); foreach (string name in names) { Console.WriteLine(name); }
So du das das vorangestellte "Auftrag" nicht willst, dann eventuell per
List<string> names = doc.Descendants().Select(el => string.Join(".", el.AncestorsAndSelf().InDocumentOrder().Skip(1).Select(anc => anc.Name.LocalName).ToArray())).ToList();
ansonsten musst du die Kriterien, nach denen die Namen zusammengefügt werden sollen, noch mal genauer erklären, so du mit den Vorschlägen das nicht selbst anpassen kannst.
MVP Data Platform Development My blog
- Als Antwort markiert mtotm Freitag, 18. Mai 2012 17:20