我有一个名为pandas.DataFrame
的{{1}}(这只是一个例子)
df
数据帧已排序,每个col1 col2 col3
A1 B1 C1
NaN B2 NaN
NaN B3 NaN
A2 B4 C2
Nan B5 C3
A3 B6 C4
NaN NaN C5
是NaN
可以被认为是包含该列中最后一个有效值的单元格。我是通过使用以下方法获得的:
col1
给出:
df[["col1"]] = df[["col1"]].fillna(method="ffill")
然后,我获得一个col1 col2 col3
A1 B1 C1
A1 B2 NaN
A1 B3 NaN
A2 B4 C2
A2 B5 C3
A3 B6 C4
A3 NaN C5
,使其键为dict
的值。这些键与包含col1
和col2
的值的字典相关联:
col3
我通过以下操作获得了data = {
"A1": {"col2": ["B1", "B2", "B3"], "col3": ["C1"]},
"A2": {"col2": ["B4", "B5"], "col3": ["C2", "C3"]},
"A3": {"col2": ["B6"], "col3": ["C4", "C5"]}
}
:
data
这是从数据帧data = {val: {"col2": group["col2"].dropna().tolist(),
"col3": group["col3"].dropna().tolist()}
for val, group in df.groupby("col1")}
到字典df
转换的最终结果。我无法实现的是相反的方法。如果得到data
,我该如何构建最初始的df
(在NaN
中也包含col1
值)?另外,请随时帮助我改善从data
到df
的转换。
编辑:data
包含df
中每个max(len(data[val]["col2"]), len(data[val]["col3"]))
的{{1}}行。如果需要val
值来填充行,则它们必须位于最后位置。例如:
data
成为
NaN
不是
data = {
"A1": {"col1": ["B1"], "col2": ["C1", "C2"]}
}
答案 0 :(得分:1)
我们可以使用cumcount
爆炸每一列,以在连接期间对齐。 col1
然后需要在重复的地方屏蔽。
import pandas as pd
df = pd.DataFrame.from_dict(data, orient='index')
df.index.name='col1'
l = []
for col in ['col2', 'col3']:
s = df.explode(col)
s['idx'] = s.groupby(level=0).cumcount()
s = s.set_index('idx', append=True)
l.append(s[col])
df = pd.concat(l, axis=1)
df = df.reset_index().drop(columns='idx')
df['col1'] = df['col1'].mask(df['col1'].duplicated())
col1 col2 col3
0 A1 B1 C1
1 NaN B2 NaN
2 NaN B3 NaN
3 A2 B4 C2
4 NaN B5 C3
5 A3 B6 C4
6 NaN NaN C5