Uso básico de la biblioteca lxml

1. Conozca lxml

lxml es una biblioteca Python XML de alto rendimiento, utilizada principalmente para analizar y generar archivos xml y html (análisis, serialización, conversión). Admite de forma nativa XPath1.0, XSLT1.0, clases de elementos personalizados e incluso interfaces de enlace de datos de estilo python. lxml se implementa en base a Cpython, y su capa inferior son dos bibliotecas de lenguaje C, libxml2 y libxslt. Por lo tanto, tiene un mayor rendimiento.

Documentación oficial: https://lxml.de/

2. Uso básico en lxml

En lxml, el módulo lxml.etree es el módulo de análisis de documentos HTML y XML más utilizado. Entre ellos, lxml.etree.Element es una clase central para procesar xml, y el objeto Element puede entenderse intuitivamente como un nodo en XML. Con la clase Element, puede implementar operaciones en nodos XML, atributos de nodos y texto dentro de los nodos.

2.1 Instalar e importar el módulo lxml

pip install lxml
from lxml import etree

2.2 Operación del nodo:

1. Cree un nodo (cree un objeto Elemento):

root = etrre.Element('root')
print(root)

2. Obtenga el nombre del nodo

print(root.tag)

3. Agregar nodos secundarios

Hay tres formas de agregar subnodos: 1. Utilice directamente el método SubElement para agregar subnodos. 2. Cree un objeto Elemento y use el método de agregar para agregar el objeto al nodo principal. 3. Cree un objeto Elemento y use el método de inserción para agregar el objeto a la posición especificada del nodo principal.

  • Use el método SubElement para agregar:
child_sub = etree.SubElement(root, 'child_sub')
  • Use el método append para agregar:
child_append = etree.Element('child_append')
root.append(child_append)
  • Use el método de inserción para agregar:
child_insert = etree.Element('child_insert')
root.insert(0, child_append)  #  第一个参数为添加的位置,第二个参数为添加的Element对象

4. Eliminar nodos secundarios:

Puede usar el método remove() para eliminar un nodo secundario específico. Use el método clear() para borrar todos los nodos secundarios

root.remove(child_sub)  # 删除名字为child_sub节点
root.clear()  # 清空root的所有子节点

5. Visita el nodo

En el objeto Elemento, hay varias formas de acceder a los nodos.

  • Los nodos se pueden orientar por medio de una lista.
  • Se puede acceder a los nodos a través de métodos como getparent().
  • Puede ubicar el nodo especificado a través de la sintaxis xpath (aún no presentado)

(1) Acceder a los nodos por medio de una lista:

child_sub = root[0]  # 通过下标来访问子节点
child_sub = root[0: 1][0]  # 通过切片的方式来访问节点
for c in root:  # 通过遍历来获取所有节点
    print(c.tag)
    
c_append_index = root.index(child_append)  # 获取节点的索引
print(len(root))  # 获取子节点的数量

(2) Acceder a los nodos a través de métodos:

  • Obtener el nodo padre: getarent()
  • Obtener todos los nodos secundarios: getchildren()
  • Obtener el nodo raíz: getroot()
  • findall(): devuelve todos los elementos coincidentes, devuelve una lista
  • find(): devuelve el primer elemento que coincide
print(child_sub.getparent().tag)  # 查询父节点
print(root.getchildren())  # 查询所有子节点
print(root.getroot())  # 获取根节点
print(root.find('b'))  # 查询第一个b标签
print(root.findall('.//b'))  # 查询所有b标签

2.3 Operaciones de atributos:

En Element, los atributos de los nodos se almacenan en forma de diccionarios.

Crear propiedades:

Hay dos formas de crear atributos. 1. Cree atributos al crear nodos. 2. Utilice el método set() para crear propiedades.

root = etree.Element('root', language='中文')  # 创建节点时创建属性

root.set('hello', 'python')  # 使用set方法为root节点添加属性

Obtener propiedades:

print(root.get('language'))  # 使用get方法获取属性
print(root['language'])
print(root.keys())
print(root.values())
print(root.items())

Modificar propiedades:

root['language'] = 'English'

2.4 Manipulación de texto

Hay muchas formas de acceder al texto xml en lxml, y puede usar los atributos text y tail para acceder al texto. También se puede acceder al texto mediante la sintaxis XPath. Aquí solo presentamos el método de usar texto y cola para obtener y establecer las propiedades del texto. El xpath se presentará en detalle más adelante.

La diferencia entre los atributos de texto y cola:

Las etiquetas en xml generalmente aparecen en pares. Pero en HTML, puede haber etiquetas individuales, como <html><body>text<br/>tail</body></html>.

  • El atributo de texto se usa para leer y establecer notas emparejadas
  • El atributo de cola se usa para leer y establecer una sola etiqueta
html = etree.Element('html')
body = etree.SubElement(html, 'body')
body.text = 'text'  # 给body标签内写入text文本内容

br = etree.SubElement('body', 'br')
br.tail = 'tail'  # 在br标签中写入tail文本内容

2.5 Análisis y serialización de archivos XML

1. Métodos para analizar archivos xml:
hay muchos métodos para analizar archivos xml, los más utilizados son fromstring, XML, HTML y parse. Los parámetros de XML y HTML pueden ser cadenas de caracteres o códigos de bytes binarios.

  • fromstring, XML, parse: devuelve un objeto Element, que es un nodo. Se utiliza principalmente para analizar fragmentos de documentos.

  • parse(): El valor devuelto es un objeto de tipo ElementTree, una estructura de árbol xml completa. parse se utiliza principalmente para analizar documentos completos, no objetos Element.

  • Parámetros:
    archivo abierto o objeto de tipo de archivo (se recomienda abrir en forma binaria
    nombre de archivo o cadena
    URL HTTP o FTP.

    Nota: el análisis desde un nombre de archivo o URL suele ser más rápido que el análisis desde un objeto de archivo .

xml_data = '<root>data</root>'

 # fromstring
root_str = etree.formstring(xml_data)
print(root_str.tag)

 # XML
root_xml = etree.XML(xml_data)
print(root_xml.tag)

 # HTML,如果没有<html>和<body>标签,则会自动补上
 root_html = etree.HTML(xml_data)
 print(root_html.tag)
 
 # parse中的参数应该是一个完整的xml或html,同样返回值是一个ElementTree类型的对象,完整的xml树结构。parse主要用来解析完整的文档。
tree =etree.parse('text')   #文件解析成元素树
root = tree.getroot()      #获取元素树的根节点
print etree.tostring(root, pretty_print=True)

2. El método de serialización del archivo xml:

Tenemos dos formas de generar un archivo xml: 1. Convierta el objeto Element en una cadena xml y luego escríbalo en el archivo. 2. Use el método write() en el objeto ElementTreee para escribir directamente el xml en el archivo.

root = '<root>data</root>'

# 将Element对象转换成xml字符串写入文件
root_str = element.tostring(root, pretty_print=True, xml_declartion=True, encoding='utf-8')
with open('text.xml', 'w', encoding='utf-8') as f:
    f.write(root_str)


# 将节点(Element对象)转为ElementTree对象。
tree = etree.ElementTree(root)
tree.write('text.xml', pretty_print=True, xml_declartion=True, encoding='utf-8')

Significado del parámetro:

  • El primer parámetro es la ruta donde se guarda el xml (incluido el nombre del archivo)
  • pretty_print: si formatear xml (embellecimiento)
  • xml_declaration: Si escribir la declaración xml, que es la primera línea de texto al principio de xml.
  • codificación: formato de codificación

Suplemento: el objeto ElementTree puede entenderse como un árbol XML completo, y cada nodo es un objeto Element. ElementPath es equivalente a XPath en XML. Se utiliza para buscar y localizar elementos de Element.


2.6 Procesamiento del espacio de nombres lxml

¿Qué es un espacio de nombres? https://www.w3school.com.cn/xml/xml_namespaces.asp

Procesamiento de análisis XML con espacios de nombres:

from lxml import etree

str_xml = """
<A xmlns="http://This/is/a/namespace">
    <B>dataB1</B>
    <B>dataB2</B>
    <B><C>datac</C></B>
</A>
"""

xml = etree.fromstring(str_xml)  # 解析字符串
ns = xml.nsmap  # 获取命名空间
print(ns)
print(ns[None])

>>> {
    
    None: 'http://This/is/a/namespace'}
>>> http://This/is/a/namespace

ns = xml.nsmap[None]  # 获取命名空间xmlns

# 1. 使用findall方法查找指定节点。
for item in xml.findall(f'{
      
      ns}b')
	print(item.text)
    
# 2. 使用xpath语法加命名空间查找指定节点
ns = {
    
    'x':root.nsmap[None]}  # 获取命名空间
b = root.xpath("//x:B", namespaces=ns)
print(b)

C = root.xapth("//x:B/X:C", namespaces=ns)
print(c)

Nota: Cuando xml lleva un espacio de nombres (xmlns), al buscar nodos, cada nivel de nodo necesita agregar un espacio de nombres. Si no se incluye el espacio de nombres, no se puede consultar el nodo.
Además, hay una forma muy sencilla de manejar los espacios de nombres, que consiste en reemplazar todos los espacios de nombres por espacios vacíos y tratarlos como nodos ordinarios.

Referencia: https://blog.csdn.net/rhx_qiuzhi/article/details/105345624


3. Use lxml para analizar el caso xml

(1) Importar la biblioteca etree de lxml

from lxml import etree

(2) Use etree.HTML para convertir la cadena html (tipo bytes o tipo str) en un objeto Element. El objeto Element tiene un método xpath y devuelve una lista de resultados

html = etree.HTML(text)
ret_list = html.xpath("xpath语法规则字符串")

(3) Tres situaciones en las que el método xpath devuelve una lista

  • Devuelve una lista vacía: de acuerdo con la cadena de la regla de sintaxis xpath, no se encuentra ningún elemento
  • Devuelve una lista de cadenas: las reglas de cadena xpath deben coincidir con el contenido del texto o el valor de un atributo
  • Devuelve una lista de objetos Element: la cadena de la regla xpath coincide con la etiqueta y los objetos Element de la lista se pueden seguir utilizando para xpath
from lxml import etree
text = '''
<div>
  <ul>
    <li class="item-1">
      <a href="link1.html">first item</a>
    </li>
    <li class="item-1">
      <a href="link2.html">second item</a>
    </li>
    <li class="item-inactive">
      <a href="link3.html">third item</a>
    </li>
    <li class="item-1">
      <a href="link4.html">fourth item</a>
    </li>
    <li class="item-0">
      a href="link5.html">fifth item</a>
  </ul>
</div>
'''

html = etree.HTML(text)  # 也可以使用XML和fromstring方法

# 获取所有的class属性为item-1的href属性
href_list = html.xpath('//li[@class="item-1"]/a/@href')
# 获取所有的class属性为item-1的text内容
text_list = html.xpath('//li[@class="item-1"]/a/text()')

# 组装成字典
for href, title in zip(href_list, title_list):
    print({
    
    f'{
      
      href}': f'{
      
      title}'})

Nota: El método lxml.etree.HTML(html_str) puede completar automáticamente las etiquetas incompletas.


4. Use lxml para generar un ejemplo de archivo xml:

from lxml import etree

# 创建element对象
root = etree.Element('root')
print(root.tag)

# 添加子节点
child_sub = etree.SubElement(root, 'child_sub')

child = etree.Element('child')
child_append = root.append(child)  # 通过append向root节点里面追加子节点
child_insert = root.insert(0, child)  # 通过insert向root节点开始的位置添加子节点

# 3.删除子节点
# root.remove(child2)

# 4.删除所有子节点
# root.clear()

# 5.以列表的方式操作子节点
print(len(root))
print root.index(child)  # 索引号

# 6.生成xml字符串写入xml文件
# 将Element对象转换成xml字符串写入文件
root_str = etree.tostring(root, pretty_print=True, xml_declaration=True, encoding='utf-8')
with open('text.xml', 'wb') as f:
    f.write(root_str)

# 将节点(Element对象)转为ElementTree对象。
tree = etree.ElementTree(root)
tree.write('text.xml', pretty_print=True, xml_declartion=True, encoding='utf-8')

Enlace de referencia: https://blog.csdn.net/ydw_ydw/article/details/82227699


5. Suplemento: sintaxis xPath

  • XPath (XML Path Language) es un lenguaje para buscar información en documentos HTML\XML y se puede utilizar para recorrer elementos y atributos en documentos HTML\XML .
  • Documento oficial de W3School: http://www.w3school.com.cn/xpath/index.asp
  • La extracción de datos en xml y html generalmente requiere el uso del módulo lxml y la sintaxis xpath

5.1 Sintaxis de selección de nodos:

Sintaxis para xpath ubicando nodos y extrayendo atributos o contenido de texto:

expresión describir
nombre del nodo Seleccione el elemento.
/ Seleccione desde el nodo raíz o haga la transición de un elemento a otro.
// Selecciona nodos en el documento desde el nodo actual que coincide con la selección, independientemente de su posición.
. Seleccione el nodo actual.
.. Seleccione el nodo principal del nodo actual.
@ Seleccione propiedades.
texto() Elegir texto.

Nota: Cuando aparece el símbolo @ al final, se usa para extraer atributos; cuando aparece en [], se usa para hacer coincidir atributos

Sintaxis para seleccionar nodos desconocidos:
los elementos html y xml desconocidos se pueden seleccionar mediante comodines

comodín describir
* Coincide con cualquier nodo de elemento.
nodo() Coincide con cualquier tipo de nodo.
  • Todas las etiquetas://*
  • Todas las propiedades://node()

5.2 Sintaxis de decoración de nodos:

Se puede obtener un nodo específico según el valor del atributo, subíndice, etc. de la etiqueta

expresión de ruta resultado
//título[@lang=“eng”] Selecciona todos los elementos de título cuyo valor de atributo lang es eng
/librería/libro[1] Selecciona el primer elemento de libro que es un elemento secundario del elemento librería.
/librería/libro[último()] Selecciona el último elemento de libro que es hijo de la librería.
/librería/libro[último()-1] Selecciona el penúltimo elemento de libro que es un elemento secundario del elemento librería.
/librería/libro[posición()>1] Seleccione el elemento de libro en librería, comenzando desde el segundo
//libro/título[texto()='Harry Potter'] Seleccione todos los elementos del título debajo del libro, solo seleccione el elemento del título cuyo texto es Harry Potter
//libro/título[contiene(texto(), “Harry”)] Seleccione todo el texto debajo del libro que contiene el elemento de título de Harry
/librería/libro[precio>35,00]/título Seleccione todos los elementos de título del elemento de libro en el elemento de librería y el valor del elemento de precio debe ser superior a 35,00.

Sobre el subíndice de xpath:

  • En xpath, la posición del primer elemento es 1
  • La posición del último elemento es last()
  • El penúltimo es el último()-1

5.3 Instalación y uso del complemento auxiliar xpath de Google Chrome

Para usar el módulo lxml para extraer datos, debemos dominar las reglas de sintaxis xpath. A continuación, echemos un vistazo al complemento auxiliar de xpath, que puede ayudarnos a practicar la sintaxis de xpath.

Instalación del complemento auxiliar xpath:

1. Descargue el complemento de Chrome XPath Helper:

2. Cambie el sufijo del archivo de crx a rar y luego descomprímalo en una carpeta con el mismo nombre

3. Arrastre la carpeta descomprimida a la interfaz de la extensión del navegador Chrome con el modo desarrollador activado

4. Después de reiniciar el navegador, haga clic en el ícono xpath en la página después de visitar la URL, y puede usarlo

5. Si se trata de un sistema operativo Linux o macOS, no es necesario realizar el paso 2 anterior y arrastrar directamente el archivo crx a la interfaz de la extensión del navegador Chrome que ha activado el modo de desarrollador.

Supongo que te gusta

Origin blog.csdn.net/weixin_57440207/article/details/116363166
Recomendado
Clasificación