
本文介绍如何将非结构化、键值交错排列的 dataframe(如姓名/值成对分布在行内)转换为标准结构化表,通过 stack + 切片技巧快速提取键列与值列并重组为规范宽表。
本文介绍如何将非结构化、键值交错排列的 dataframe(如姓名/值成对分布在行内)转换为标准结构化表,通过 stack + 切片技巧快速提取键列与值列并重组为规范宽表。
在实际数据处理中,我们常遇到“伪表格”结构:原始数据并非标准的行列对齐格式,而是以键(key)和值(value)交替出现在同一行中的非结构化形式。例如如下 DataFrame:
import pandas as pd
df = pd.DataFrame([
['Name', 'khan', 'Salary', 5000],
['Age', 42, 'phone', '01783232575']
])
目标是将其规整为标准宽表,其中列名为 ['Name', 'Age', 'Salary', 'Phone'],单行记录对应各字段取值。
核心思路是:利用 stack() 将二维结构压平为带层级索引的一维 Series,再按奇偶位置分离键与值。具体步骤如下:
-
压平并提取数组
df.stack().values将所有非空元素按列优先顺序展开为一维 NumPy 数组,结果为:array(['Name', 'khan', 'Salary', 5000, 'Age', '42', 'phone', '01783232575'], dtype=object)
可见键(
'Name','Salary','Age','phone')位于偶数索引(0, 2, 4, 6),对应值('khan',5000,42,'01783232575')位于奇数索引(1, 3, 5, 7)。 -
构造新 DataFrame
直接切片赋值:arr = df.stack().values result = pd.DataFrame( data=[arr[1::2]], # 所有奇数位 → 值(作为数据行) columns=arr[::2] # 所有偶数位 → 键(作为列名) )输出为:
Name Salary Age phone 0 khan 5000 42 01783232575
⚠️ 注意事项:
- 若需严格控制列顺序(如要求
['Name', 'Age', 'Salary', 'Phone']),上述方法依赖原始数据中键的出现顺序。若原始表中键位置不固定(如'Age'出现在第 0 行),建议先显式定义列顺序并重排:desired_cols = ['Name', 'Age', 'Salary', 'phone'] result = result[desired_cols] # 自动对齐,缺失列将填充 NaN
-
phone列名未标准化为'Phone',可在构造后统一重命名:result.rename(columns={'phone': 'Phone'}, inplace=True)。 - 若存在多行记录(即多个实体),该方法默认仅处理单组键值对;扩展场景需结合
groupby或分块处理。
该方案简洁高效,避免循环与冗长条件判断,充分发挥 pandas 向量化操作优势,适用于清洗 OCR 输出、日志解析或低质量 Excel 导入等典型非结构化数据场景。










