Seite 1 von 1

Was macht dieser Code? (XML, ElementTree, namespaces)

Verfasst: Freitag 14. Februar 2020, 09:03
von Hase
Hallo, ich arbeite in letzter Zeit viel mit XML-Dateien. Aber XML ohne namespaces ermitteln zu können ist nicht wirklich zielführend. LXML stellt hierfür die Funktion "nsmap" zur Verfügung. Doch auch ElementTree kann das, nämlich mit

Code: Alles auswählen

ns = dict([node for _, node in ET.iterparse(filename, events=['start-ns'])])
Das funktioniert gut, aber warum? Was hat es mit diesem "node for _, node in ..." auf sich? Kann mir jemand in Worten erklären, was das bedeutet?

Vielen Dank!

Re: Was macht dieser Code? (XML, ElementTree, namespaces)

Verfasst: Freitag 14. Februar 2020, 09:21
von Sirius3
@Hase: was meinst Du damit? Hast Du Dir angeschaut, was iterparse zurückliefert? Geht es Dir um die Listcomprehension, die Du nicht verstehst?

Ich habe schon viel mit XML-Dateien gearbeitet, aber namespaces mußte ich auf diese Weise noch nie ermitteln. Wie ein Namespace in XML abgekürzt wird, ist nämlich irrelevant, einzig die URL ist bindend.

Re: Was macht dieser Code? (XML, ElementTree, namespaces)

Verfasst: Freitag 14. Februar 2020, 09:32
von Hase
Hallo, wenn ich ein Element aus der Datei suchen möchte, brauche ich den kompletten namespace

e = element.find(name, ns)

sonst wird nichts gefunden. Listcemprehensions sind mir schon bekannt, aber wofür steht das "_" ? Ist das ein Variablenname?

Re: Was macht dieser Code? (XML, ElementTree, namespaces)

Verfasst: Freitag 14. Februar 2020, 09:36
von Hase
Ah, sorry, das oben ist ich wirklich richtig. Die Suche sieht so aus:

e = element.find('gml:Envelope', ns)

Re: Was macht dieser Code? (XML, ElementTree, namespaces)

Verfasst: Freitag 14. Februar 2020, 09:55
von Sirius3
Und das ist falsch. Niemand garantiert, dass `gml` immer `gml` heißt, oder dass `gml` an http://www.opengis.net/gml/3.2 gebunden ist.
Daher ist der richtige Aufruf mit einem fixen Namespace-Wörterbuch, das nicht aus dem XML gelesen wird:

Code: Alles auswählen

GML_NAMESPACES = {
    'irgendein_namespace_name': 'http://www.opengis.net/gml/3.2',
}

e = element.find('irgendein_namespace_name:Envelope', GML_NAMESPACES)
`irgendein_namespace_name` ist hier nur ein Beispiel, dass man irgendeinen Namespacenamen benutzen könnte, üblich ist wahrscheinlich gml, aber das ist halt nicht fest vorgegeben.

Das `_` steht für einen Variablennamen, wie jeder andere Variablenamen. Es ist Konvention, wenn an einer Stelle eine Variable stehen muß, die aber nicht gebraucht wird, den Namen `_` zu benutzen.