2009-09-11 20 views
23

tengo una estructura XML que se parece a la siguiente, pero en una escala mucho más grande:lectura XML usando Python minidom y iterar sobre cada nodo

<root> 
    <conference name='1'> 
     <author> 
      Bob 
     </author> 
     <author> 
      Nigel 
     </author> 
    </conference> 
    <conference name='2'> 
     <author> 
      Alice 
     </author> 
     <author> 
      Mary 
     </author> 
    </conference> 
</root> 

Para esto, se utiliza el siguiente código:

dom = parse(filepath) 
conference=dom.getElementsByTagName('conference') 
for node in conference: 
    conf_name=node.getAttribute('name') 
    print conf_name 
    alist=node.getElementsByTagName('author') 
    for a in alist: 
     authortext= a.nodeValue 
     print authortext 

Sin embargo, el authortext que se imprime es 'Ninguno'. Intenté jugar con variaciones como las que se muestran a continuación, pero hace que mi programa se rompa.

authortext=a[0].nodeValue 

La salida correcta debe ser:

1 
Bob 
Nigel 
2 
Alice 
Mary 

Pero lo que consigo es:

1 
None 
None 
2 
None 
None 

Alguna sugerencia sobre cómo hacer frente a este problema?

Respuesta

23

su authortext es de tipo 1 (ELEMENT_NODE), normalmente necesita TEXT_NODE para obtener una cadena. Esto funcionará

a.childNodes[0].nodeValue 
0

He jugado un poco con él un poco, y aquí es lo que tengo que trabajar:

# ... 
authortext= a.childNodes[0].nodeValue 
print authortext 

que conduce a la producción de:

 
C:\temp\py>xml2.py 
1 
Bob 
Nigel 
2 
Alice 
Mary 

No puedo decir exactamente por qué tiene que acceda al childNode para obtener el texto interno, pero al menos eso es lo que estaba buscando.

6

Los nodos de elemento no tienen un nodeValue. Tienes que mirar los nodos de texto dentro de ellos. Si sabe que siempre hay un nodo de texto dentro, puede decir element.firstChild.data (los datos son los mismos que nodeValue para los nodos de texto).

Tenga cuidado: si no hay contenido de texto, no habrá secundarios Los nodos de texto y element.firstChild serán nulos, lo que hará que el acceso .data falle.

forma rápida de obtener el contenido de los nodos de texto niño directos:

text= ''.join(child.data for child in element.childNodes if child.nodeType==child.TEXT_NODE) 

En DOM Nivel 3 Núcleo se obtiene la propiedad textContent puede utilizar para obtener el texto desde el interior de un elemento de forma recursiva, pero no lo hace minidom apoye esto (algunas otras implementaciones DOM de Python sí).

2

Acceso rápido:

node.getElementsByTagName('author')[0].childNodes[0].nodeValue 
0

Ya que siempre tiene un valor de datos de texto por autor puede utilizar element.firstChild.data

dom = parseString(document) 
conferences = dom.getElementsByTagName("conference") 

# Each conference here is a node 
for conference in conferences: 
    conference_name = conference.getAttribute("name") 
    print 
    print conference_name.upper() + " - " 

    authors = conference.getElementsByTagName("author") 
    for author in authors: 
     print " ", author.firstChild.data 
    # for 

    print 
Cuestiones relacionadas