为什么 xlrd 读取的列数错误?

Why is xlrd reading the wrong number of columns?

当我读取 .xls 文件时,xlrd 就像在位置 0 处有一个空列一样,并且永远不会读取最后一列(如果从 0 开始计数,则编号为 58);第一列被跳过,最后一列消失。

当我保存文件(作为 .xls 或 .xlsx)并再次执行整个过程时,问题就消失了。保存时,Excel告诉我可能存在兼容性问题。我需要自动执行此过程,这就是为什么我想避免手动保存文件的原因。

# Loading the 'converted' file
wb = xlrd.open_workbook(converted_file_path) 
sheet = wb.sheet_by_index(0)

print('Row',len(sheet.row(3)),sheet.row(3))
# Prints: Row 59 [text:'Client Number', ...


# Loading the original file
wb = xlrd.open_workbook(original_file_path) 
print('Row',len(sheet.row(3)),sheet.row(3))
# Prints: Row 58 [empty:'', text:'Client Number', ...

print(sheet.cell_value(0,5))
# Prints nothing, while there is a number at cell (0,5)

如果您在 Windows,并且您发现使用 Excel 加载/保存文件以某种方式修复了您的文件,那么您可以使用 Excel 本身来执行此操作初始转换。然后应该使用 xlrd 使用您现有的代码正确加载。例如:

import win32com.client as win32
import xlrd

excel = win32.gencache.EnsureDispatch('Excel.Application')

wb = excel.Workbooks.Open(r'input.xls')
excel.DisplayAlerts = False
wb.DoNotPromptForConvert = True
wb.CheckCompatibility = False
wb.SaveAs(r"output.xlsx", FileFormat=51, ConflictResolution=2)
excel.Application.Quit()

# Loading the 'converted' file
wb = xlrd.open_workbook('output.xlsx') 
sheet = wb.sheet_by_index(0)

print('Row',len(sheet.row(3)),sheet.row(3))
# Prints: Row 59 [text:'Client Number', ...

感谢 Martin 建议 win32com 修复,但我发现了实际问题。它与 xlrd 如何 Python 在内存中加载 sheets 有关。也许在加载工作簿时弄乱 on_demand 参数会有所作为,但无论如何,这就是发生的事情:

我需要名为 "Report X" 的 sheet,其中 X 是某个数字,所以我这样查找:

for sheet in wb.sheets():
    if 'Report' in sheet.name:
        report_sheet = sheet
        break

然后,我改成了

for sheet in wb.sheets():
    if 'Report' in sheet.name:
        report_sheet = sheet
        # removed the break

现在可以了。