我有 3 个不同的 dfs,除了 1 个 ID 之外,都有不同的列。 我并不真正关心不同的数据,我最终想要的只是一个包含 ID 和另外三列的 DF,如果 DF 中存在 ID,则每列包含 1,如果 ID 存在,则每列包含 0(或无)不存在。
一个例子:
DF1
index irrelevant columns
A
B
C
DF2
index irrelevant columns2
A
B
F
DF3
index irrelevant columns3
A
F
G
最终的DF
index DF1 DF2 DF3
A 1 1 0
B 1 1 0
C 1 0 0
F 0 1 1
G 0 0 1
到目前为止,我正在做的事情(这在内存方面非常糟糕)是(考虑索引 = ID)
df1['df1'] = 1
df1 = pd.DataFrame(df1['df1']) # There has to be a way around this that does not require to create a new DF
df2['df2'] = 1
df2 = pd.DataFrame(df2['df2'])
df3['df3'] = 1
df3 = pd.DataFrame(df3['df3'])
data = pd.concat([df1,df2,df3], sort=False, axis=1)
我确信必须有一种更好的方法,不需要我仅使用该列创建一个新的 df,但我尝试过的所有操作都写入了 dfs 的所有列,而我不需要那样.
最佳答案
将列表理解与 DataFrame
构造函数和 Index.to_series
一起使用,然后通过 notna
检查非缺失值并将掩码转换为整数:
dfs = {'DF1': DF1, 'DF2': DF2, 'DF3': DF3}
comp = {k: v.index.to_series() for k, v in dfs.items()}
df = pd.DataFrame(comp).notna().astype(int)
构造函数使用 Series
的另一个解决方案:
comp = {k: pd.Series(1, index=v.index) for k, v in dfs.items()}
df = pd.DataFrame(comp).fillna(0).astype(int)
<小时/>
print (df)
DF1 DF2 DF3
A 1 1 1
B 1 1 0
C 1 0 0
F 0 1 1
G 0 0 1
另一个解决方案 MultiLabelBinarizer
:
dfs = {'DF1': DF1, 'DF2': DF2, 'DF3': DF3}
L = [v.index for k, v in dfs.items()]
from sklearn.preprocessing import MultiLabelBinarizer
mlb = MultiLabelBinarizer()
df = pd.DataFrame(mlb.fit_transform(L),index=list(dfs.keys())).T
print (df)
DF1 DF2 DF3
0 1 1 1
1 1 1 0
2 1 0 0
3 0 1 1
4 0 0 1
关于python - pandas concat/更新 3 dfs,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52983960/