You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python openpyxl批量转换xlsx为csv时数据重复写入问题

需求背景
  • 共有24个Excel文件,需要将每个.xlsx文件的各工作表数据导出为对应的csv文件
  • 目前已实现基础数据拷贝逻辑,但生成的csv文件中数据重复写入10次,初步判断问题出在for循环逻辑
  • 曾尝试将writerows()替换为writerow(),但问题未解决,当前正在学习openpyxl读写对象相关用法
原有实现代码
import openpyxl, os, csv
from pathlib import Path

for excelFile in os.listdir('./excelspreadsheets'):
    if excelFile.endswith('.xlsx'): # Skip non xlsx files, load the workbook object
        wb = openpyxl.load_workbook('./excelspreadsheets/' + excelFile)
        for sheetName in wb.sheetnames:

            # Loop through every sheet in the workbook
            sheet = wb[sheetName]
            sheetTitle = sheet.title

            # Create the CSV filename from the Excel filename and sheet title
            p = Path(excelFile)
            excelFileStemName = p.stem
            CsvFilename = excelFileStemName + '_' + sheetTitle + '.csv'

            # Create the csv.writer object for this CSV file
            print(f'Creating filename {CsvFilename}...')
            outputFile = open(CsvFilename, 'w', newline='')
            outputWriter = csv.writer(outputFile)

            # Create reader object for each excel sheet
            fileObj = open('./excelspreadsheets/' + excelFile)
            fileReaderObj = csv.reader(fileObj)

            # Loop through every row in the excel sheet
            for rowNum in range(1, sheet.max_row + 1):
                rowData = [] # append each cell to this list
                
                # Loop through each cell in the row
                for colNum in range(1, sheet.max_column + 1):
                    rowData.append(sheet.values)

            # write the rowData list to the CSV file. 
            for row in rowData:
                outputWriter.writerows(row)

            outputFile.close()
异常现象
  • 新生成的csv文件写入的数据内容本身正确,但会重复写入10次,而非仅写入1次
问题原因
  1. 存在冗余无效代码:使用openpyxl加载工作簿后,额外编写了用csv.reader读取xlsx文件的逻辑,xlsx是二进制格式,csv.reader无法正确解析,这段代码完全不生效可以删除
  2. 取值逻辑错误:内层列循环中rowData.append(sheet.values)的写法有误,sheet.values是整个工作表所有行值的生成器对象,不是单个单元格的值,每遍历一列就会往rowData中存入一次全表数据,遍历多少列就重复存多少次,这是数据重复的核心原因
  3. 写入逻辑冗余:外层行循环结束后,又额外遍历了一次rowData调用writerows,进一步放大了数据重复的问题
修复后代码
import openpyxl, os, csv
from pathlib import Path

for excelFile in os.listdir('./excelspreadsheets'):
    if excelFile.endswith('.xlsx'):
        # 加载工作簿,data_only=True读取单元格计算后的值而非公式
        wb = openpyxl.load_workbook('./excelspreadsheets/' + excelFile, data_only=True)
        for sheetName in wb.sheetnames:
            sheet = wb[sheetName]
            # 拼接csv文件名
            excelFileStemName = Path(excelFile).stem
            CsvFilename = f"{excelFileStemName}_{sheet.title}.csv"
            print(f'Creating filename {CsvFilename}...')
            
            # 用上下文管理器操作文件,自动完成关闭操作
            with open(CsvFilename, 'w', newline='', encoding='utf-8') as outputFile:
                outputWriter = csv.writer(outputFile)
                # 直接遍历sheet.values获取每行数据,无需手动循环行列号
                for row in sheet.values:
                    outputWriter.writerow(row)
优化说明
  • 删除了无效的csv读取xlsx的冗余逻辑
  • 直接遍历sheet.values获取行数据,避免手动循环行列号时的取值错误
  • 写入单行数据使用writerow(),传入单行值列表即可
  • 使用with上下文管理器管理文件IO,无需手动调用close(),避免资源泄漏
  • 加载工作簿时增加data_only=True参数,直接读取单元格计算后的实际值,而非公式字符串
  • 写入文件时指定encoding='utf-8',避免中文乱码问题

内容的提问来源于stack exchange,提问作者Luca

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.31 00:12:41