Convierta datos a DataFrame en Python

Dec 08 2020

Con la ayuda de @JaSON, aquí hay un código que me permite obtener los datos en la tabla de html local y el código usa selenio

from selenium import webdriver

driver = webdriver.Chrome("C:/chromedriver.exe")
driver.get('file:///C:/Users/Future/Desktop/local.html')
counter = len(driver.find_elements_by_id("Section3"))
xpath = "//div[@id='Section3']/following-sibling::div[count(preceding-sibling::div[@id='Section3'])={0} and count(following-sibling::div[@id='Section3'])={1}]"
print(counter)

for i in range(counter):
    print('\nRow #{} \n'.format(i + 1))
    _xpath = xpath.format(i + 1, counter - (i + 1))
    cells = driver.find_elements_by_xpath(_xpath)
    for cell in cells:
         value = cell.find_element_by_xpath(".//td").text
         print(value)

¿Cómo se pueden convertir estas filas en una tabla válida que pueda exportar a un archivo csv? Aquí está el enlace HTML localhttps://pastebin.com/raw/hEq8K75C

** @Paul Brennan: Después de intentar editar el contador counter-1, obtuve 17 filas para omitir el error de la fila 18 temporalmente, obtuve el nombre de archivo.txt y aquí está la instantánea de la salida

Respuestas

1 PaulBrennan Dec 08 2020 at 19:56

He modificado su código para hacer una salida simple. Esto no es muy pitónico ya que no utiliza la creación vectorizada del Dataframe, pero así es como funciona. Primero configure pandas, segundo configure un marco de datos (pero aún no conocemos las columnas) luego configure las columnas en la primera pasada (esto causará problemas si hay longitudes de columna variables Luego ingrese los valores en el marco de datos

import pandas as pd
from selenium import webdriver

driver = webdriver.Chrome("C:/chromedriver.exe")
driver.get('file:///C:/Users/Future/Desktop/local.html')
counter = len(driver.find_elements_by_id("Section3"))
xpath = "//div[@id='Section3']/following-sibling::div[count(preceding-sibling::div[@id='Section3'])={0} and count(following-sibling::div[@id='Section3'])={1}]"
print(counter)

df = pd.Dataframe()

for i in range(counter):
    print('\nRow #{} \n'.format(i + 1))
    _xpath = xpath.format(i + 1, counter - (i + 1))
    cells = driver.find_elements_by_xpath(_xpath)
    if i == 0:
        df = pd.DataFrame(columns=cells) # fill the dataframe with the column names
    for cell in cells:
        value = cell.find_element_by_xpath(".//td").text
        #print(value)
        if not value:  # check the string is not empty
            # always puting the value in the first item
            df.at[i, 0] = value # put the value in the frame

df.to_csv('filename.txt') # output the dataframe to a file

La forma de mejorar esto es poner los elementos en una fila en un diccionario y colocarlos en el marco de datos. pero estoy escribiendo esto en mi teléfono, así que no puedo probarlo.

YasserKhalil Dec 11 2020 at 11:32

Con la gran ayuda de @Paul Brennan, pude modificar el código para obtener el resultado final deseado

import pandas as pd
from selenium import webdriver

driver = webdriver.Chrome("C:/chromedriver.exe")
driver.get('file:///C:/Users/Future/Desktop/local.html')
counter = len(driver.find_elements_by_id("Section3"))
xpath = "//div[@id='Section3']/following-sibling::div[count(preceding-sibling::div[@id='Section3'])={0} and count(following-sibling::div[@id='Section3'])={1}]"
finallist = []

for i in range(counter):
    #print('\nRow #{} \n'.format(i + 1))
    rowlist=[]
    _xpath = xpath.format(i + 1, counter - (i + 1))
    cells = driver.find_elements_by_xpath(_xpath)
    #if i == 0:
        #df = pd.DataFrame(columns=cells) # fill the dataframe with the column names
    for cell in cells:
        try:
            value = cell.find_element_by_xpath(".//td").text
            rowlist.append(value)
        except:
            break
    finallist.append(rowlist)
    
df = pd.DataFrame(finallist)
df[df.columns[[2, 0, 1, 7, 9, 8, 3, 5, 6, 4]]]

El código funciona bien ahora pero es demasiado lento. ¿Hay alguna forma de hacerlo más rápido?