Python优雅解析Excel并将数据进行结构化转换
作者:秋天的落叶铺满小路
在 Python 后端开发、数据分析、自动化办公等场景中,读取 Excel 文件并转换为可高效处理的程序数据结构是极高频的需求。
很多开发者处理 Excel 数据时,习惯直接通过数字下标取值,也就是 row[2]、col[5] 这类硬编码写法。这种方式看似快速,却会陷入严重的行列索引耦合问题:代码可读性极差、后期维护成本极高,一旦表格列顺序、字段调整,整段代码都可能报错重构。
本文将基于 Spire.XLS 库,通过三层递进的代码方案,实现 Excel 数据的结构化转换,依次落地 二维列表、字典列表、自定义实体对象列表 三种数据结构。适配不同业务场景,彻底解决索引硬编码痛点,让 Excel 解析代码更规范、可读、可维护、可扩展。
一、环境准备
本文所有示例基于 spire.xls 库实现,该库支持高兼容的 Excel 读写、格式解析、批量处理,无需依赖 Office 环境,跨平台适配性强。
执行以下命令快速安装依赖:
pip install spire.xls
二、方案一:原生二维列表(基础只读结构)
2.1 实现思路
这是最基础、最直接的 Excel 数据读取方式。通过获取工作表的已用数据区域,逐行、逐单元格遍历取值,最终将所有数据存入二维列表,完整保留 Excel 原始的行列矩阵结构。
2.2 完整代码实现
from spire.xls import Workbook
# 加载Excel文件、获取工作表
workbook = Workbook()
workbook.LoadFromFile("SalesReport.xlsx")
sheet = workbook.Worksheets[0]
# 获取表格已使用的数据区域
cell_range = sheet.AllocatedRange
# 初始化二维列表存储数据
excel_data = []
# 遍历行和列,逐单元格取值
for row_idx in range(cell_range.RowCount):
single_row = []
for col_idx in range(cell_range.ColumnCount):
# spire.xls 行列下标从1开始,需要做偏移适配
single_row.append(cell_range[row_idx + 1, col_idx + 1].Value)
excel_data.append(single_row)
# 释放文件资源
workbook.Dispose()
2.3 优缺点与适用场景
核心特点:完全复刻 Excel 矩阵结构,代码逻辑简单、无额外转换成本。
致命缺陷:数据访问完全依赖数字索引 excel_data[row][col],代码语义完全缺失。若表格字段顺序调整、新增/删除列,所有索引下标需要批量修改,极易引发 Bug。
适用场景:仅用于临时数据预览、简单矩阵计算、一次性脚本,不推荐正式生产项目使用。
三、方案二:字典列表(通用业务首选结构)
3.1 实现思路
针对二维列表索引硬编码的痛点,我们优化结构:提取表格首行作为字段键(Key),每一行数据映射为一个字典(Value),最终形成字典列表数据结构。
该方案将「数字索引取值」升级为「字段名语义取值」,彻底解耦列顺序依赖,是绝大多数 Excel 数据处理场景的最优通用方案。
3.2 完整代码实现
from spire.xls import Workbook
workbook = Workbook()
workbook.LoadFromFile("SalesReport.xlsx")
sheet = workbook.Worksheets[0]
cell_range = sheet.AllocatedRange
# 提取首行作为表头字段
rows = list(cell_range.Rows)
headers = [cell_range[1, col_idx + 1].Value for col_idx in range(cell_range.ColumnCount)]
# 遍历数据行,映射为字典列表
data_list = []
# 跳过表头,从第二行开始读取业务数据
for row in rows[1:]:
row_dict = {}
for idx, cell in enumerate(row.Cells):
# 表头字段为键,单元格值为值
row_dict[headers[idx]] = cell.Value
data_list.append(row_dict)
workbook.Dispose()
3.3 优缺点与适用场景
核心优势:通过语义化字段取值(data_list[0]["销售额"]),代码可读性大幅提升;列顺序调整不影响业务代码,兼容性极强;天然适配 JSON 序列化、Pandas 数据分析、API 数据传输。
微小不足:无固定数据类型约束,单元格数据默认原生类型,需要手动做类型转换和参数校验。
适用场景:数据清洗、批量数据导入导出、接口参数封装、日常数据分析,推荐作为绝大多数业务场景的首选方案。
四、方案三:自定义实体对象列表(强类型高可扩展结构)
4.1 实现思路
对于数据结构固定、业务逻辑复杂的 Excel 场景,字典结构的弱类型特性会带来类型混乱、无代码提示、无法封装业务逻辑等问题。
因此我们做最终层级抽象:定义业务实体类,将每行 Excel 数据映射为实体对象,实现强类型约束、自动代码补全、自定义数据校验和业务方法封装。
4.2 完整代码实现
# 定义业务实体类,固定数据结构与字段类型
class Employee:
def __init__(self, name: str, age: int | None, department: str):
# 员工姓名
self.name = name
# 员工年龄(可空)
self.age = age
# 所属部门
self.department = department
# 可自定义业务方法,扩展能力
def is_adult(self) -> bool:
"""判断是否为成年员工"""
return self.age >= 18 if self.age else False
from spire.xls import Workbook
workbook = Workbook()
workbook.LoadFromFile("EmployeeData.xlsx")
sheet = workbook.Worksheets[0]
cell_range = sheet.AllocatedRange
employee_list = []
# 遍历业务数据行
for row in list(cell_range.Rows)[1:]:
# 手动类型转换 + 空值兼容处理
name = row.Cells[0].Value
age = int(row.Cells[1].Value) if row.Cells[1].Value else None
department = row.Cells[2].Value
# 实例化实体对象并存入列表
emp = Employee(name, age, department)
employee_list.append(emp)
workbook.Dispose()
4.3 核心亮点与适用场景
核心优势:
- 强类型约束:手动完成数据类型转换、空值兜底,避免数据类型异常;
- 代码可扩展:可在实体类中封装业务计算、数据校验、状态判断等方法;
- 开发效率高:IDE 支持字段智能补全,杜绝字段名拼写错误;
- 代码规范性强:数据与业务逻辑高度内聚,符合面向对象编程思想。
适用场景:数据结构长期稳定、需要复杂业务计算、需要参数校验、追求工程化规范的正式项目。
五、三种数据结构选型指南
根据业务复杂度、使用场景快速选择最优方案,避免过度开发或设计不足:
| 数据结构 | 优势 | 劣势 | 适用场景 |
|---|---|---|---|
| 二维列表 | 实现简单、无转换成本 | 无语义、索引硬编码、维护困难 | 临时脚本、数据预览、矩阵计算 |
| 字典列表 | 语义清晰、通用性强、兼容序列化 | 弱类型、无结构化约束 | 绝大多数数据分析、数据同步、接口传输场景 |
| 自定义对象列表 | 强类型、可扩展、可封装业务逻辑、易维护 | 少量代码冗余、需要提前定义实体类 | 正式工程项目、结构化稳定数据、复杂业务逻辑处理 |
六、关键注意点:资源释放避坑
所有示例中均包含 workbook.Dispose() 方法,这是 spire.xls 使用的核心避坑点。
spire.xls 会持续占用本地 Excel 文件句柄,若读取文件后不主动释放资源,在批量循环处理文件、长期运行的服务中,会出现文件占用、内存泄漏、无法二次编辑文件等问题。
因此,每次文件读取完成后,必须主动调用 Dispose 释放工作簿资源。
七、总结
从「二维列表数字索引」到「字典语义取值」,再到「自定义对象强类型封装」,三层数据结构的迭代,本质是代码从「机器思维」向「业务思维」的升级。
简单场景无需过度设计,通用场景优先字典列表,工程化复杂场景首选自定义实体对象。合理选择 Excel 数据结构化方式,能极大降低代码冗余、减少线上 Bug、提升项目可维护性。
到此这篇关于Python优雅解析Excel并将数据进行结构化转换的文章就介绍到这了,更多相关Python解析Excel内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!
