Pandas leer tablas HTML

de Pandaspd.read_html()La función puede analizar automáticamente los datos de tablas HTML de la página web y convertirlos en un DataFrame. Esto es muy útil en escenarios como extracción de datos web, análisis de precios de acciones, obtención de información financiera, etc.


Uso básico

read_html()La función busca y lee todos los elementos de tabla HTML en la página web, devolviendo una lista de DataFrames.

Leer una tabla individual

Ejemplo

import pandas as pd

# Leer todas las tablas de la página web
# Nota: requiere soporte de las bibliotecas lxml y beautifulsoup4
# pip install lxml beautifulsoup4

# Leer desde URL
tables = pd.read_html("https://example.com/table.html")

# Ver el número de tablas encontradas
print(f"Se encontraron {len(tables)} tablas")

# Obtener la primera tabla
df = tables[0]
print(df.head())

Leer múltiples tablas

Una página web puede contener múltiples tablas,read_html()devuelve una lista, a la que se puede acceder por índice:

Ejemplo

import pandas as pd

# Supongamos que la página web tiene varias tablas
tables = pd.read_html("https://example.com/data.html")

# Recorrer todas las tablas
for i, table in enumerate(tables):
    print(f"\n"=== Tabla {i+1} ===")
    print(f"Forma: {table.shape}")
    print(table.head(3))

Explicación detallada de los parámetros comunes

Parámetro Descripción Ejemplo
io Fuente de entrada, puede ser una URL, ruta de archivo o cadena "page.html"
match Coincidencia regex, filtra tablas que contienen texto específico match="销售额"
header Especifica el índice de la fila de encabezado header=0
attrs Filtra tablas mediante atributos HTML attrs={"id": "table1"}
skiprows Omite filas especificadas skiprows=[0, 1]
na_values Especifica cadenas que se tratan como valores faltantes na_values=["N/A"]

Filtrar tablas con el parámetro match

Ejemplo

import pandas as pd

# Usar el parámetro match para devolver solo tablas que contengan texto específico
# Por ejemplo: leer solo tablas que contengan "acciones"
tables = pd.read_html(
    "https://example.com/finance.html",
    match="acciones"
)

if tables:
    df = tables[0]
    print(df)

Ubicar tablas con precisión con el parámetro attrs

Ejemplo

import pandas as pd

# Ubicar la tabla mediante atributos HTML
# Por ejemplo: obtener la tabla con id="stock-table"
tables = pd.read_html(
    "https://example.com/data.html",
    attrs={"id": "stock-table"}  # Buscar el elemento table con id="stock-table"
)

# O ubicar mediante class
tables = pd.read_html(
    "https://example.com/data.html",
    attrs={"class": "data-table"}
)

df = tables[0]
print(df)

Ejemplo práctico: extraer datos de acciones de páginas web

El siguiente ejemplo muestra cómo extraer datos de listas de acciones de sitios web financieros:

Ejemplo

import pandas as pd
from io import StringIO


# Crear un contenido HTML simulado para la demostración
# Al usarlo en la práctica, reemplazar con una URL real
html_content = '''
<table border="1">
    <tr>
<th>Código de acción</th>
<th>Nombre de la acción</th>
<th>Precio de cierre</th>
<th>Cambio porcentual</th>
    </tr>
    <tr>
        <td>600519</td>
<td>Kweichow Moutai</td>
        <td>1850.00</td>
        <td>2.35%</td>
    </tr>
    <tr>
        <td>000858</td>
<td>Wuliangye</td>
        <td>185.50</td>
        <td>-1.20%</td>
    </tr>
    <tr>
        <td>601318</td>
<td>Ping An de China</td>
        <td>52.30</td>
        <td>0.85%</td>
    </tr>
</table>
'''


# Leer la tabla desde una cadena

tables = pd.read_html(StringIO(html_content))

df = tables[0]

print("Tabla original:")
print(df)
print()

# Limpieza de datos: procesar la columna de cambio porcentual
df["Cambio porcentual"] = df["Cambio porcentual"].str.replace("%", "").astype(float)
df["Precio de cierre"] = df["Precio de cierre"].astype(float)

print("Datos después de la limpieza:")
print(df)

La función de StringIO es: disfrazar una cadena como un objeto de archivo, de modo que pandas la procese siguiendo la lógica de lectura de flujos de archivo, en lugar de interpretarla erróneamente como una ruta o URL.

Salida:

原始表格:
     股票代码  股票名称     收盘价     涨跌幅
0  600519  贵州茅台  1850.0   2.35%
1     858   五粮液   185.5  -1.20%
2  601318  中国平安    52.3   0.85%

清洗后的数据:
     股票代码  股票名称     收盘价   涨跌幅
0  600519  贵州茅台  1850.0  2.35
1     858   五粮液   185.5 -1.20
2  601318  中国平安    52.3  0.85

Leer tablas de Wikipedia

Ejemplo

import pandas as pd

# Leer tablas de la página de Wikipedia
# Tomemos como ejemplo la lista de población por país
url = "https://en.wikipedia.org/wiki/List_of_countries_by_population_(United_Nations)"

try:
    tables = pd.read_html(url)
    print(f"La página tiene {len(tables)} tablas en total")

    # Normalmente la primera tabla es la que necesitamos
    df = tables[0]
    print(df.head(10))
except Exception as e:
    print(f"Error de lectura: {e}")
    print("Asegúrese de instalar las bibliotecas necesarias: pip install lxml beautifulsoup4")

Limpieza y procesamiento de datos

Las tablas leídas de páginas web generalmente requieren una limpieza adicional antes de poder usarse para análisis.

Operaciones comunes de limpieza

Ejemplo

import pandas as pd
from io import StringIO

# Simular una tabla con varios tipos de datos sucios
html_content = '''
<table>
<tr><th>Fecha</th><th>Producto</th><th>Ventas</th><th>Notas</th></tr>
<tr><td>2024-01-01</td><td>Producto A</td><td>1,234</td><td>N/A</td></tr>
<tr><td>2024-01-02</td><td>Producto B</td><td>567</td><td>Agotado</td></tr>
<tr><td>2024-01-03</td><td>Producto C</td><td>--</td><td>Sin registrar</td></tr>
</table>
'''


df = pd.read_html(StringIO(html_content))[0]
print("Datos originales:")
print(df)
print()

# Pasos de limpieza
# 1. Renombrar columnas
df.columns = ["Fecha", "Producto", "Ventas", "Notas"]

# 2. Manejar valores faltantes
df = df.replace(["N/A", "--", "Sin registrar", "Agotado"], pd.NA)

# 3. Limpiar la columna numérica (eliminar comas)
df["Ventas"] = df["Ventas"].str.replace(",", "").replace(pd.NA, None)
df["Ventas"] = pd.to_numeric(df["Ventas"], errors="coerce")

# 4. Convertir fecha
df["Fecha"] = pd.to_datetime(df["Fecha"])

print("Después de la limpieza:")
print(df)
print("\nTipo de datos:)
print(df.dtypes)

Salida:

原始数据:
           日期   产品    销量   备注
0  2024-01-01  产品A  1234  NaN
1  2024-01-02  产品B   567   缺货
2  2024-01-03  产品C    --  未统计

清洗后:
          日期   产品      销量    备注
0 2024-01-01  产品A  1234.0   NaN
1 2024-01-02  产品B   567.0  <NA>
2 2024-01-03  产品C     NaN  <NA>

数据类型:
日期    datetime64[ns]
产品            object
销量           float64
备注            object
dtype: object

Precauciones y problemas comunes

1. Instalar bibliotecas de dependencias

read_html()Se necesitanlxmlybeautifulsoup4bibliotecas:

pip install lxml beautifulsoup4

2. Problemas de red

Al leer URLs de red, es posible encontrar latencia de red o restricciones de acceso. Se recomienda añadir una configuración de tiempo de espera adecuada o utilizar caché local.

3. Estructura de tabla compleja

Algunas tablas de páginas web usan estructuras complejas como celdas combinadas o tablas anidadas, lo que puede provocar fallos de análisis. En este caso, se puede intentar usar BeautifulSoup para analizar el HTML directamente.

4. Integridad de los datos

Los datos de las páginas web pueden cambiar en cualquier momento. Se recomienda verificar la integridad de los datos después de la lectura y compararlos con la fuente original.

Al extraer datos de páginas web, respete las reglas de robots.txt del sitio y las leyes y regulaciones correspondientes. No realice solicitudes con demasiada frecuencia para no sobrecargar el servidor.


Resumen

pd.read_html()Es una herramienta poderosa para extraer datos de tablas web, ya que puede convertir rápidamente tablas HTML en DataFrames. En uso real, se debe prestar atención a la instalación de bibliotecas de dependencias, problemas de red, limpieza de datos sucios, etc. Los datos extraídos generalmente requieren un procesamiento adicional para el análisis; se recomienda combinarlos con las funciones de limpieza de datos de Pandas.

Otras extensiones