基于openpyxl的Python阅卷程序输出不符合预期问题求助
阅卷器程序输出异常修复
问题背景
我正在开发一款阅卷器程序,使用openpyxl读取Excel工作簿,工作簿包含两个工作表:
- 存储考生姓名及所选答案的工作表
- 存储标准答案的工作表
程序需要新建一个工作表,写入每位考生的答题情况(正确显示答案,错误则标注正确答案),目前新建工作表的操作已完成,但输出结果不符合预期。之前自己实现了数字转列字母的工具,后来发现openpyxl支持直接用sheet.cell(row=行号, column=列号).value操作单元格,不过当前问题出在输出逻辑上。
相关表格截图
- 考生答卷工作表:

- 标准答案工作表:

- 当前错误输出:

- 期望输出:

原代码
from openpyxl import load_workbook from ABCDE import ABCD workbook = 'CETT.xlsx' rsp = load_workbook(workbook, data_only=True) rspage = rsp[input('Name of the responses sheet: ')] copage = rsp[input('Name of the correction sheet: ')] n_ques = int(input('Number of questions: ')) n_answ = rspage.max_row - 1 correct = [] responses = [] correction = [] def cct(): for i in range(n_ques): cell = ABCD(i + 1) + '2' correct.append(copage[cell].value) a = [] def rrp(): global a for i in range(n_answ): for j in range(n_ques + 1): c = ABCD(j + 1) a.append(rspage[c + str(i + 2)].value) responses.append(a) a = [] def crt(): crpage = rsp.create_sheet('correction') for i in range(n_answ): b = [] b.append(responses[i][0]) crpage[ABCD(i+n_answ) + str(1)] = responses[i][0] for j in range(n_ques): if responses[i][j+1] == correct[j]: b.append(responses[i][j+1]) crpage[ABCD(j+2) + str(i+1)] = responses[i][j+1] else: b.append('w: ' + str(responses[i][j+1]) + ' c: ' + str(correct[j])) crpage[ABCD(j+2) + str(i+1)] = 'w: ' + str(responses[i][j+1]) + ' c: ' + str(correct[j]) correction.append(b) rsp.save('CETT.xlsx') cct() rrp() crt()
问题分析
当前输出异常的核心原因:
- 考生姓名位置错误:原代码中
crpage[ABCD(i+n_answ) + str(1)] = responses[i][0]把考生姓名写入了第i+n_answ列的第1行,完全偏离了期望的第一列(A列)每行对应一个考生的布局。 - 行号逻辑错误:写入答题情况时用了
str(i+1),但第1行应该留作表头,考生数据需从第2行开始。 - 自定义的
ABCD转换容易出错,不如直接使用openpyxl的cell(row, column)方法直观可靠。
修复方案及代码
修正后的代码解决了上述问题,同时添加了表头,使用cell()方法简化单元格操作:
from openpyxl import load_workbook workbook = 'CETT.xlsx' rsp = load_workbook(workbook, data_only=True) rspage = rsp[input('Name of the responses sheet: ')] copage = rsp[input('Name of the correction sheet: ')] n_ques = int(input('Number of questions: ')) n_answ = rspage.max_row - 1 correct = [] responses = [] correction = [] def cct(): # 读取标准答案,直接用cell方法,第2行是答案行 for col in range(1, n_ques + 1): correct.append(copage.cell(row=2, column=col).value) def rrp(): # 读取考生姓名和答案 for row in range(2, rspage.max_row + 1): student_data = [] for col in range(1, n_ques + 2): student_data.append(rspage.cell(row=row, column=col).value) responses.append(student_data) def crt(): crpage = rsp.create_sheet('correction') # 写入表头 crpage.cell(row=1, column=1).value = '姓名' for q in range(1, n_ques + 1): crpage.cell(row=1, column=q + 1).value = f'Q{q}' # 写入每位考生的答题情况 for idx, student in enumerate(responses): # 写入姓名:第idx+2行,第1列 crpage.cell(row=idx + 2, column=1).value = student[0] b = [student[0]] for q_idx in range(n_ques): student_ans = student[q_idx + 1] std_ans = correct[q_idx] # 写入答题情况:第idx+2行,第q_idx+2列 if student_ans == std_ans: crpage.cell(row=idx + 2, column=q_idx + 2).value = student_ans b.append(student_ans) else: error_text = f'w: {student_ans} c: {std_ans}' crpage.cell(row=idx + 2, column=q_idx + 2).value = error_text b.append(error_text) correction.append(b) rsp.save('CETT.xlsx') cct() rrp() crt()
修复说明
- 移除了自定义的
ABCD转换工具,全程使用cell(row, column)方法操作单元格,避免列号转换错误。 - 新增表头行,让输出结构更清晰,符合期望的格式。
- 修正了考生姓名和答题数据的行/列位置,确保姓名在第一列每行对应一个考生,答题数据对应到正确的题目列。
- 简化了考生数据读取的逻辑,去掉了全局变量
a,代码更易维护。
内容的提问来源于stack exchange,提问作者Pyton
相关产品推荐
相关产品推荐

