J'utilise actuellement pandas pour lire un fichier Excel et présenter ses noms de feuilles à l'utilisateur, afin qu'il puisse sélectionner la feuille qu'il souhaite utiliser. Le problème est que les fichiers sont vraiment gros (70 colonnes x 65 000 lignes), il faut jusqu'à 14 secondes pour charger sur un ordinateur portable (les mêmes données dans un fichier CSV prennent 3 secondes).
Mon code dans panda va comme ceci:
xls = pandas.ExcelFile(path)
sheets = xls.sheet_names
J'ai déjà essayé xlrd, mais j'ai obtenu des résultats similaires. C'était mon code avec xlrd:
xls = xlrd.open_workbook(path)
sheets = xls.sheet_names
Alors, quelqu'un peut-il suggérer un moyen plus rapide de récupérer les noms de feuille d'un fichier Excel que de lire le fichier entier?
vous pouvez utiliser la bibliothèque xlrd et ouvrir le classeur avec l'indicateur "on_demand = True", afin que les feuilles ne soient pas chargées automatiquement.
Vous pouvez ensuite récupérer les noms de feuille de la même manière que les pandas:
import xlrd
xls = xlrd.open_workbook(r'<path_to_your_Excel_file>', on_demand=True)
print xls.sheet_names() # <- remeber: xlrd sheet_names is a function, not a property
J'ai essayé xlrd, pandas, openpyxl et d'autres bibliothèques de ce type et toutes semblent prendre un temps exponentiel à mesure que la taille du fichier augmente à mesure qu'il lit le fichier entier. Les autres solutions mentionnées ci-dessus où elles utilisaient "on_demand" ne fonctionnaient pas pour moi. La fonction suivante fonctionne pour les fichiers xlsx.
def get_sheet_details(file_path):
sheets = []
file_name = os.path.splitext(os.path.split(file_path)[-1])[0]
# Make a temporary directory with the file name
directory_to_extract_to = os.path.join(settings.MEDIA_ROOT, file_name)
os.mkdir(directory_to_extract_to)
# Extract the xlsx file as it is just a Zip file
Zip_ref = zipfile.ZipFile(file_path, 'r')
Zip_ref.extractall(directory_to_extract_to)
Zip_ref.close()
# Open the workbook.xml which is very light and only has meta data, get sheets from it
path_to_workbook = os.path.join(directory_to_extract_to, 'xl', 'workbook.xml')
with open(path_to_workbook, 'r') as f:
xml = f.read()
dictionary = xmltodict.parse(xml)
for sheet in dictionary['workbook']['sheets']['sheet']:
sheet_details = {
'id': sheet['sheetId'], # can be @sheetId for some versions
'name': sheet['name'] # can be @name
}
sheets.append(sheet_details)
# Delete the extracted files directory
shutil.rmtree(directory_to_extract_to)
return sheets
Étant donné que tous les xlsx sont essentiellement des fichiers zippés, nous extrayons les données xml sous-jacentes et lisons directement les noms des feuilles du classeur, ce qui prend une fraction de seconde par rapport aux fonctions de la bibliothèque.
Analyse comparative: (Sur un fichier xlsx de 6 Mo avec 4 feuilles)
Pandas, xlrd: 12 secondes
openpyxl: 24 secondes
Méthode proposée: 0,4 seconde