我有大型Pandas数据框,看起来像这样:
Label1 Label2 Label3 Id1 Val1 Id2 Val2 Id3 Val3
0 A B C a 0.80 b 0.79 c 0.29
1 A B D None NaN None NaN e 0.06
2 E B F None NaN b 0.86 None NaN
3 E G H b 0.16 None NaN f 0.34
我想将Id1之前的列转换为类似的字典:
Label1 Label2 Label3 kvp
0 A B C {'a': 0.8, 'b': 0.79, 'c': 0.29}
1 A B D {'e': 0.06}
2 E B F {'b': 0.86}
3 E G H {'b': 0.16, 'f': 0.34}
这种选择和转换是否有Pandas成语,或者我是否必须编写代码来遍历行?
答案 0 :(得分:1)
您可以通过获取相关列,将它们重新整形为2列numpy数组,然后将其转换为dict来为单行创建字典:
>>> a
Label1 Label2 Label3 Id1 Val1 Id2 Val2 Id3 Val3
0 A B C a 0.80 b 0.79 c 0.29
1 A B D None NaN None NaN e 0.06
2 E B F None NaN b 0.86 None NaN
3 E G H b 0.16 None NaN f 0.34
>>> a.irow(0)[3:].reshape(3,2)
array([['a', 0.80000000000000004],
['b', 0.79000000000000004],
['c', 0.28999999999999998]], dtype=object)
>>> dict(_)
{'b': 0.79000000000000004, 'c': 0.28999999999999998, 'a': 0.80000000000000004}
您可以编写一个使用该原则的函数来创建旧行的新行:
def adjust_row(row):
kvp_data = row[3:].valid()
kvp_data = kvp_data.reshape(kvp_data.size//2, 2)
kvp = dict(kvp_data)
return row[:3].append(pd.Series({'kvp': kvp}))
请注意,这会将None
和NaN
排除在valid()
之外,计算临时numpy数组的相应行数。验证它对任何给定行都是正确的:
>>> adjust_row(a.irow(1))
Label1 A
Label2 B
Label3 D
kvp {'e': 0.06}
dtype: object
完成后,您可以使用数据框架上的apply
方法将其应用于每一行:
>>> a.apply(adjust_row, axis=1)
Label1 Label2 Label3 kvp
0 A B C {'b': 0.79, 'c': 0.29, 'a': 0.8}
1 A B D {'e': 0.06}
2 E B F {'b': 0.86}
3 E G H {'f': 0.34, 'b': 0.16}