Pandas多列层级转置求助:按患者、品牌分组并按日期展开
问题需求
现有数百名患者的测试结果(成功S/失败F)按日期分布,需要按患者、品牌、状态类型分组,并将日期作为列展开,得到指定格式的结果。
示例数据
import pandas as pd df2 = pd.DataFrame({ 'patient': ['one', 'one', 'one', 'one','one', 'one', 'one', 'one','two', 'two','two','two','two', 'two','two','two'], 'Brand': ['A', 'A', 'A', 'A', 'B', 'B','B','B','A','A','A','A','B', 'B', 'B', 'B'], 'date': ['11/1/2022', '11/2/2022', '11/3/2022', '11/4/2022', '11/5/2022', '11/6/2022','11/7/2022', '11/8/2022', '11/9/2022','11/10/2022', '11/11/2022','11/12/2022', '11/1/2022', '11/2/2022', '11/3/2022', '11/4/2022'], 'Status1': ['S', 'F', 'F', 'F', 'S', 'F','F', 'F', 'S','F', 'F','F','S', 'F', 'F', 'F'], 'Status2': ['F', 'S', 'F', 'F', 'F', 'S','F', 'F', 'F','S', 'F','F','F', 'S', 'F', 'F'], 'Status3': ['F', 'F', 'S', 'F', 'F', 'F','S', 'F', 'F','F', 'S','F','F', 'F', 'S', 'F'], 'Status4': ['F', 'F', 'F', 'S', 'F', 'F','F', 'S', 'F','F', 'F','S','F', 'F', 'F', 'S'] })
期望结果
转换后的数据为多层索引结构:
- 行维度:患者、品牌、状态类型的组合
- 列维度:各个测试日期
- 单元格:对应状态在指定日期的测试结果(S/F)
示意表格如下:
| patient | Brand | 状态类型 | 11/1/2022 | 11/2/2022 | 11/3/2022 | ... |
|---|---|---|---|---|---|---|
| one | A | Status1 | S | F | F | ... |
| one | A | Status2 | F | S | F | ... |
| one | A | Status3 | F | F | S | ... |
| ... | ... | ... | ... | ... | ... | ... |
解决方案
通过melt转长表、pivot转宽表的组合操作实现需求:
# 1. 将多列状态转为长表,保留患者、品牌、日期作为标识列 melted_df = df2.melt(id_vars=['patient', 'Brand', 'date'], var_name='状态类型', value_name='结果') # 2. 按患者、品牌、状态类型分组,将日期转为列,填充对应测试结果 result_df = melted_df.pivot(index=['patient', 'Brand', '状态类型'], columns='date', values='结果') # 3. 移除列索引的名称(可选,让表格更整洁) result_df.columns.name = None # 打印最终结果 print(result_df)
执行上述代码后,即可得到与期望格式一致的数据表。
内容的提问来源于stack exchange,提问作者Murali
相关产品推荐
相关产品推荐

