Pergunta

Python tem várias maneiras para analisar XML ...

Eu entendo o básico de analisar com SAX . Ele funciona como um analisador de fluxo, com uma API orientada a eventos.

Eu entendo a DOM analisador também. Ele lê o XML na memória e converte-lo para objetos que podem ser acessados ??com Python.

De um modo geral, foi fácil escolher entre os dois, dependendo do que você precisava fazer, restrições de memória, desempenho, etc.

(Espero que eu estou correto até agora.)

Uma vez que o Python 2.5, também temos ElementTree . Como isso se compara com DOM e SAX? Que é mais semelhante a? Por que é melhor do que os analisadores anteriores?

Foi útil?

Solução

ElementTree é muito mais fácil de usar, porque representa uma árvore XML (basicamente) como uma estrutura de listas, e atributos são representados como dicionários.

ElementTree precisa de muito menos memória de árvores XML de DOM (e, portanto, é mais rápido), ea análise sobrecarga via iterparse é comparável a SAX. Além disso, iterparse retorna estruturas parciais, e você pode manter a memória para uso constante durante a análise, descartando as estruturas logo que você processá-los.

ElementTree, como em Python 2.5, tem apenas um pequeno conjunto de recursos em comparação com bibliotecas XML full-blown, mas é o suficiente para muitas aplicações. Se você precisa de um analisador de validação ou suporte XPath completa, lxml é o caminho a percorrer. Por um longo tempo, que costumava ser bastante instável, mas eu não tive nenhum problema com ele desde 2.1.

ElementTree desvia do DOM, onde os nós têm acesso ao seu pai e irmãos. Manuseio de documentos reais em vez de armazenamentos de dados também é um pouco complicado, porque nós de texto não são tratados como nós reais. No XML trecho

<a>This is <b>a</b> test</a>

O test corda será o chamado tail de elemento b.

Em geral, eu recomendo ElementTree como padrão para todo o processamento de XML com o Python, e DOM ou SAX como as soluções para problemas específicos.

Outras dicas

implementação DOM mínima:

Fazer a ligação .

Python fornece uma implementação completa, W3C-padrão de XML DOM ( xml.dom ) e um mínimo, xml.dom.minidom . Este último é mais simples e menor do que a plena implementação. No entanto, a partir de uma "perspectiva de análise", tem todos os prós e contras do DOM padrão -. Ou seja, ele carrega tudo na memória

Considerando um arquivo XML básico:

<?xml version="1.0"?>
<catalog>
    <book isdn="xxx-1">
      <author>A1</author>
      <title>T1</title>
    </book>
    <book isdn="xxx-2">
      <author>A2</author>
      <title>T2</title>
    </book>
</catalog>

Um analisador Python possível usando minidom é:

import os
from xml.dom import minidom
from xml.parsers.expat import ExpatError

#-------- Select the XML file: --------#
#Current file name and directory:
curpath = os.path.dirname( os.path.realpath(__file__) )
filename = os.path.join(curpath, "sample.xml")
#print "Filename: %s" % (filename)

#-------- Parse the XML file: --------#
try:
    #Parse the given XML file:
    xmldoc = minidom.parse(filepath)
except ExpatError as e:
    print "[XML] Error (line %d): %d" % (e.lineno, e.code)
    print "[XML] Offset: %d" % (e.offset)
    raise e
except IOError as e:
    print "[IO] I/O Error %d: %s" % (e.errno, e.strerror)
    raise e
else:
    catalog = xmldoc.documentElement
    books = catalog.getElementsByTagName("book")

    for book in books:
        print book.getAttribute('isdn')
        print book.getElementsByTagName('author')[0].firstChild.data
        print book.getElementsByTagName('title')[0].firstChild.data

Note que xml.parsers.expat é uma interface Python para o analisador XML Expat não-validação (docs.python.org/2/library/pyexpat.html).

O xml.dom suprimentos pacote também a classe de exceção DOMException , mas não é supperted em minidom !

O ElementTree XML API:

Fazer a ligação .

ElementTree é muito mais fácil de usar e que requer menos memória do que XML DOM. Além disso, uma implementação C está disponível ( xml.etree.cElementTree ).

Um analisador Python possível usando ElementTree é:

import os
from xml.etree import cElementTree  # C implementation of xml.etree.ElementTree
from xml.parsers.expat import ExpatError  # XML formatting errors

#-------- Select the XML file: --------#
#Current file name and directory:
curpath = os.path.dirname( os.path.realpath(__file__) )
filename = os.path.join(curpath, "sample.xml")
#print "Filename: %s" % (filename)

#-------- Parse the XML file: --------#
try:
    #Parse the given XML file:
    tree = cElementTree.parse(filename)
except ExpatError as e:
    print "[XML] Error (line %d): %d" % (e.lineno, e.code)
    print "[XML] Offset: %d" % (e.offset)
    raise e
except IOError as e:
    print "[XML] I/O Error %d: %s" % (e.errno, e.strerror)
    raise e
else:
    catalogue = tree.getroot()

    for book in catalogue:
        print book.attrib.get("isdn")
        print book.find('author').text
        print book.find('title').text

parse do ElementTree () é como DOM, enquanto iterparse () é como SAX. Na minha opinião, ElementTree é melhor do que DOM e SAX na medida em que fornece API mais fácil trabalhar com.

ElementTree tem API mais Python. É também na biblioteca padrão agora assim usá-lo reduz as dependências.

Eu realmente prefiro lxml , pois tem API como ElementTree, mas também tem boas características e executa adicionais bem.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top