xls al convertidor de csv

Estoy usando win32.client en python para convertir mi archivo .xlsx y .xls en un archivo .csv. Cuando ejecuto este código está dando un error. Mi código es:

def convertXLS2CSV(aFile): '''converts a MS Excel file to csv w/ the same name in the same directory''' print "------ beginning to convert XLS to CSV ------" try: import win32com.client, os from win32com.client import constants as c excel = win32com.client.Dispatch('Excel.Application') fileDir, fileName = os.path.split(aFile) nameOnly = os.path.splitext(fileName) newName = nameOnly[0] + ".csv" outCSV = os.path.join(fileDir, newName) workbook = excel.Workbooks.Open(aFile) workbook.SaveAs(outCSV, c.xlCSVMSDOS) # 24 represents xlCSVMSDOS workbook.Close(False) excel.Quit() del excel print "...Converted " + nameOnly + " to CSV" except: print ">>>>>>> FAILED to convert " + aFile + " to CSV!" convertXLS2CSV("G:\\hello.xlsx") 

No puedo encontrar el error en este código. Por favor ayuda.

Yo usaría xlrd – es más rápido, multiplataforma y funciona directamente con el archivo. Una cosa a tener en cuenta, no funciona en archivos xlsx, por lo que tendría que guardar su archivo de Excel como xls. Edición: A partir de la versión 0.8.0, xlrd lee los archivos XLS y XLSX.

  import xlrd import csv def csv_from_excel(): wb = xlrd.open_workbook('your_workbook.xls') sh = wb.sheet_by_name('Sheet1') your_csv_file = open('your_csv_file.csv', 'wb') wr = csv.writer(your_csv_file, quoting=csv.QUOTE_ALL) for rownum in xrange(sh.nrows): wr.writerow(sh.row_values(rownum)) your_csv_file.close() 

Yo usaría pandas . Las partes pesadas computacionalmente están escritas en cython o c-extensiones para acelerar el proceso y la syntax es muy limpia. Por ejemplo, si desea convertir “Sheet1” del archivo “your_workbook.xls” en el archivo “your_csv.csv”, simplemente use la función de nivel superior read_excel y el método to_csv de la clase DataFrame la siguiente manera:

 import pandas as pd data_xls = pd.read_excel('your_workbook.xls', 'Sheet1', index_col=None) data_xls.to_csv('your_csv.csv', encoding='utf-8') 

La configuración de encoding='utf-8' alivia el UnicodeEncodeError mencionado en otras respuestas.

Tal vez alguien encuentre útil este código de código listo para usar. Permite crear CSV de todas las hojas de cálculo en el libro de Excel.

introduzca la descripción de la imagen aquí

 # -*- coding: utf-8 -*- import xlrd import csv from os import sys def csv_from_excel(excel_file): workbook = xlrd.open_workbook(excel_file) all_worksheets = workbook.sheet_names() for worksheet_name in all_worksheets: worksheet = workbook.sheet_by_name(worksheet_name) with open('{}.csv'.format(worksheet_name), 'wb') as your_csv_file: wr = csv.writer(your_csv_file, quoting=csv.QUOTE_ALL) for rownum in xrange(worksheet.nrows): wr.writerow([unicode(entry).encode("utf-8") for entry in worksheet.row_values(rownum)]) if __name__ == "__main__": csv_from_excel(sys.argv[1]) 

Usaría csvkit , que usa xlrd (para xls) y openpyxl (para xlsx) para convertir casi cualquier dato tabular a csv.

Una vez instalado, con sus dependencias, se trata de:

 python in2csv myfile > myoutput.csv 

Se ocupa de todos los problemas de detección de formato, por lo que puede pasarlo por cualquier fuente de datos tabular. También es multiplataforma (sin dependencia de win32).

@andi He probado tu código, funciona muy bien, PERO

En mis hojas hay una columna como esta.

2013-03-06T04: 00: 00

fecha y hora en la misma celda

Se confunde durante la exportación, es así en el archivo exportado

41275.0416667

otras columnas están bien.

csvkit, en el otro lado, hace bien con esa columna pero solo exporta UNA hoja, y mis archivos tienen muchos.

xlsx2csv es más rápido que pandas y xlrd.

 xlsx2csv -s 0 crunchbase_monthly_.xlsx cruchbase 

archivo de Excel por lo general viene con n nombre de hoja.

 -s is sheetname index. 

luego, se creará la carpeta cruchbase, cada hoja perteneciente a xlsx se convertirá en un solo csv.

ps csvkit es impresionante también.

Citando una respuesta de Scott Ming , que funciona con un libro de trabajo que contiene varias hojas:

Aquí hay un script en python getsheets.py ( espejo ), debe instalar pandas y xlrd antes de usarlo.

Ejecuta esto:

 pip3 install pandas xlrd # or `pip install pandas xlrd` 

¿Cómo funciona?

 $ python3 getsheets.py -h Usage: getsheets.py [OPTIONS] INPUTFILE Convert a Excel file with multiple sheets to several file with one sheet. Examples: getsheets filename getsheets filename -f csv Options: -f, --format [xlsx|csv] Default xlsx. -h, --help Show this message and exit. 

Convertir a varios xlsx:

 $ python3 getsheets.py goods_temp.xlsx Sheet.xlsx Done! Sheet1.xlsx Done! All Done! 

Convertir a varios csv:

 $ python3 getsheets.py goods_temp.xlsx -f csv Sheet.csv Done! Sheet1.csv Done! All Done! 

getsheets.py :

 # -*- coding: utf-8 -*- import click import os import pandas as pd def file_split(file): s = file.split('.') name = '.'.join(s[:-1]) # get directory name return name def getsheets(inputfile, fileformat): name = file_split(inputfile) try: os.makedirs(name) except: pass df1 = pd.ExcelFile(inputfile) for x in df1.sheet_names: print(x + '.' + fileformat, 'Done!') df2 = pd.read_excel(inputfile, sheetname=x) filename = os.path.join(name, x + '.' + fileformat) if fileformat == 'csv': df2.to_csv(filename, index=False) else: df2.to_excel(filename, index=False) print('\nAll Done!') CONTEXT_SETTINGS = dict(help_option_names=['-h', '--help']) @click.command(context_settings=CONTEXT_SETTINGS) @click.argument('inputfile') @click.option('-f', '--format', type=click.Choice([ 'xlsx', 'csv']), default='xlsx', help='Default xlsx.') def cli(inputfile, format): '''Convert a Excel file with multiple sheets to several file with one sheet. Examples: \b getsheets filename \b getsheets filename -f csv ''' if format == 'csv': getsheets(inputfile, 'csv') else: getsheets(inputfile, 'xlsx') cli() 

Usar xlrd es una forma defectuosa de hacer esto, porque pierde los formatos de fecha en Excel.

Mi caso de uso es el siguiente.

Tome un archivo de Excel con más de una hoja y convierta cada uno de ellos en un archivo propio.

He hecho esto usando la biblioteca xlsx2csv y llamándolo usando un subproceso.

 import csv import sys, os, json, re, time import subprocess def csv_from_excel(fname): subprocess.Popen(["xlsx2csv " + fname + " --all -d '|' -i -p " "'' > " + 'test.csv'], shell=True) return lstSheets = csv_from_excel(sys.argv[1]) time.sleep(3) # system needs to wait a second to recognize the file was written with open('[YOUR PATH]/test.csv') as f: lines = f.readlines() firstSheet = True for line in lines: if line.startswith(''): if firstSheet: sh_2_fname = line.replace('', '').strip().replace(' - ', '_').replace(' ','_') print(sh_2_fname) sh2f = open(sh_2_fname+".csv", "w") firstSheet = False else: sh2f.close() sh_2_fname = line.replace('', '').strip().replace(' - ', '_').replace(' ','_') print(sh_2_fname) sh2f = open(sh_2_fname+".csv", "w") else: sh2f.write(line) sh2f.close() 

He probado todas las respuestas, pero fueron demasiado lentas para mí. Si tiene instalado Excel, puede utilizar el COM.

Pensé que inicialmente sería más lento ya que cargaría todo para la aplicación Excel real, pero no es para archivos enormes. Tal vez debido a que el algoritmo para abrir y guardar archivos ejecuta un código comstackdo altamente optimizado, los chicos de Microsoft ganan mucho dinero por ello después de todo.

 import sys import os import glob from win32com.client import Dispatch def main(path): excel = Dispatch("Excel.Application") if is_full_path(path): process_file(excel, path) else: files = glob.glob(path) for file_path in files: process_file(excel, file_path) excel.Quit() def process_file(excel, path): fullpath = os.path.abspath(path) full_csv_path = os.path.splitext(fullpath)[0] + '.csv' workbook = excel.Workbooks.Open(fullpath) workbook.Worksheets(1).SaveAs(full_csv_path, 6) workbook.Saved = 1 workbook.Close() def is_full_path(path): return path.find(":") > -1 if __name__ == '__main__': main(sys.argv[1]) 

Este es un código muy simple y no buscará errores, ni ayuda de impresión ni nada, solo creará un archivo csv para cada archivo que coincida con el patrón que ingresó en la función para que pueda procesar por lotes una gran cantidad de archivos con solo iniciar la aplicación Excel una vez.

Podemos usar Pandas lib de Python para convertir un archivo xls a un archivo csv El siguiente código convertirá el archivo xls a un archivo csv. importar pandas como pd

Lea el archivo de Excel de la ruta local:

 df = pd.read_excel("C:/Users/IBM_ADMIN/BU GPA Scorecard.xlsx",sheetname=1) 

Recortar los espacios presentes en las columnas:

 df.columns = df.columns.str.strip() 

Envíe el dataframe a un archivo CSV que tendrá un símbolo de tubería delimitado y sin índice:

 df.to_csv("C:/Users/IBM_ADMIN/BU GPA Scorecard csv.csv",sep="|",index=False) 

Por mucho que odie confiar en el software propietario de Windows Excel, que no es multiplataforma, mi prueba de csvkit para .xls, que usa xlrd bajo el capó, no pudo analizar las fechas correctamente (incluso cuando se usan los parámetros de la línea de comandos para especificar strptime formato).

Por ejemplo, este archivo xls , cuando se analiza con csvkit , convertirá la celda G1 del 12/31/2002 a 37621 , mientras que cuando se convierte a csv a través de excel -> save_as (utilizando a continuación) la celda G1 será "December 31, 2002" .

 import re import os from win32com.client import Dispatch xlCSVMSDOS = 24 class CsvConverter(object): def __init__(self, *, input_dir, output_dir): self._excel = None self.input_dir = input_dir self.output_dir = output_dir if not os.path.isdir(self.output_dir): os.makedirs(self.output_dir) def isSheetEmpty(self, sheet): # https://archive.is/RuxR7 # WorksheetFunction.CountA(ActiveSheet.UsedRange) = 0 And ActiveSheet.Shapes.Count = 0 return \ (not self._excel.WorksheetFunction.CountA(sheet.UsedRange)) \ and \ (not sheet.Shapes.Count) def getNonEmptySheets(self, wb, as_name=False): return [ \ (sheet.Name if as_name else sheet) \ for sheet in wb.Sheets \ if not self.isSheetEmpty(sheet) \ ] def saveWorkbookAsCsv(self, wb, csv_path): non_empty_sheet_names = self.getNonEmptySheets(wb, as_name=True) assert (len(non_empty_sheet_names) == 1), \ "Expected exactly 1 sheet but found %i non-empty sheets: '%s'" \ %( len(non_empty_sheet_names), "', '".join(name.replace("'", r"\'") for name in non_empty_sheet_names) ) wb.Worksheets(non_empty_sheet_names[0]).SaveAs(csv_path, xlCSVMSDOS) wb.Saved = 1 def isXlsFilename(self, filename): return bool(re.search(r'(?i)\.xls$', filename)) def batchConvertXlsToCsv(self): xls_names = tuple( filename for filename in next(os.walk(self.input_dir))[2] if self.isXlsFilename(filename) ) self._excel = Dispatch('Excel.Application') try: for xls_name in xls_names: csv_path = os.path.join(self.output_dir, '%s.csv' %os.path.splitext(xls_name)[0]) if not os.path.isfile(csv_path): workbook = self._excel.Workbooks.Open(os.path.join(self.input_dir, xls_name)) try: self.saveWorkbookAsCsv(workbook, csv_path) finally: workbook.Close() finally: if not len(self._excel.Workbooks): self._excel.Quit() self._excel = None if __name__ == '__main__': self = CsvConverter( input_dir='C:\\data\\xls\\', output_dir='C:\\data\\csv\\' ) self.batchConvertXlsToCsv() 

Lo anterior tomará un input_dir contiene .xls y los output_dir a output_dir como .csv; assert que hay exactamente 1 hoja no vacía en los .xls; Si necesita manejar varias hojas en múltiples csv, entonces deberá editar saveWorkbookAsCsv .