如何在Python中展开数组字典对象(实现R的tidyr::unnest功能)
R的tidyr::unnest功能的Python实现
问题描述
将R代码迁移至Python时,需要实现类似data <- tidyr::unnest(data)的嵌套数据展开功能。尝试了pd.json_normalize(df, sep=' ')和pd.DataFrame(A).explode('id'),但未得到预期输出。
输入数据
{ "id": [ "3", "3", "3" ], "a": [ "1", "1", "1" ], "b": [ "1", "2", "3" ], "c": [ "1", "1", "1" ], "d": [ "1", "1", "1" ], "e": [ 0, 0, 0 ] }
期望输出
"id" "a" "b" "c" "d" "e" "3" "1" "1" "1" "1" 0 "3" "1" "2" "1" "1" 0 "3" "1" "3" "1" "1" 0 "3" "1" "4" "1" "1" 0 "3" "1" "5" "1" "1" 0
解决方案
情况1:输入为标量+列表结构(推测输入存在笔误)
如果真实输入是仅b为多值列表,其余字段为单一值(符合unnest典型使用场景),直接用pandas的explode方法即可:
import pandas as pd # 修正后的输入数据 input_data = { "id": "3", "a": "1", "b": ["1", "2", "3", "4", "5"], "c": "1", "d": "1", "e": 0 } # 构造DataFrame并展开b列 df = pd.DataFrame([input_data]) result = df.explode('b') # 输出符合格式的结果 print(result.to_csv(sep=' ', index=False, header=True))
情况2:基于你提供的输入扩展到5行
如果必须基于给定的输入(所有字段为长度3的列表)生成5行结果,可重新构造b列并让其余字段重复对应值:
import pandas as pd # 原始输入数据 input_data = { "id": ["3", "3", "3"], "a": ["1", "1", "1"], "b": ["1", "2", "3"], "c": ["1", "1", "1"], "d": ["1", "1", "1"], "e": [0, 0, 0] } # 构造初始DataFrame df = pd.DataFrame(input_data) # 生成包含1-5的b列,其余字段取第一个值重复 new_df = pd.DataFrame({ "id": df['id'].iloc[0], "a": df['a'].iloc[0], "b": ["1", "2", "3", "4", "5"], "c": df['c'].iloc[0], "d": df['d'].iloc[0], "e": df['e'].iloc[0] }) # 输出符合格式的结果 print(new_df.to_csv(sep=' ', index=False, header=True))
之前方法无效的原因
pd.json_normalize用于展开嵌套JSON结构(如字典中的子字典/列表),不适合处理同长度列表转多行的场景。explode('id')是对id列执行展开,但你的id列是重复的同值列表,展开后不会改变行数,自然得不到预期结果。需要针对多值列(如b)使用explode。
内容的提问来源于stack exchange,提问作者user23287007
相关产品推荐
相关产品推荐

