我想将
set_1
中的 set_2
和 df_2
列中的列表与 ins
中的 df_1
列进行比较,以查找所有常见元素。
我已经开始对一行和一列进行操作,但我不知道如何比较两个 dfs 之间的所有行以获得所需的结果。
这是我比较第一行中的
set_1
和 ins
的代码:
import pandas as pd
d1 = {'chr': [1, 1], 'start': [64, 1000], 'end': [150, 2000], 'family': ['a', 'b'],
'ins': [['P1-12', 'P1-22', 'P1-25', 'P1-28', 'P1-90'],
['P1-6', 'P1-89', 'P1-92', 'P1-93']]}
df1 = pd.DataFrame.from_dict(data=d1)
d2 = {'set_1': [['P1-12', 'P1-25', 'P1-28'], ['P1-6', 'P1-89', 'P1-93']],
'set_2': [['P1-89', 'P1-92', 'P1-93'], ['P1-25', 'P1-28', 'P1-90']]}
df2 = pd.DataFrame.from_dict(data=d2)
matches = [x for x in df2.iloc[0, 0] if x in df1.iloc[0, 4]]
我的输入数据只有一小部分(在原始输入中,df1 包含 ~13k 行,df2 包含 ~90 行):
df1:
chr start end family ins
0 1 64 150 a [P1-12, P1-22, P1-25, P1-28, P1-90]
1 1 1000 2000 b [P1-6, P1-89, P1-92, P1-93]
df2:
set_1 set_2
0 [P1-12, P1-25, P1-28] [P1-89, P1-92, P1-93]
1 [P1-6, P1-89, P1-93] [P1-25, P1-28, P1-90]
所需的输出应如下所示:
chr start end family df2_index ins_set1 ins_set2
0 1 64 150 a 0 [P1-12, P1-25, P1-28] []
1 1 64 150 a 1 [] [P1-25, P1-28, P1-90]
2 1 1000 2000 b 0 [] [P1-89, P1-92, P1-93]
3 1 1000 2000 b 1 [P1-6, P1-89, P1-93] []
merge
,然后使用set
来提高效率:
out = df1.merge(df2, how='cross')
cols = list(df2)
ins = out.pop('ins').apply(set)
for c in cols:
out[c] = [[x for x in lst if x in ref]
for ref, lst in zip(ins, out[c])]
输出:
chr start end family set_1 set_2
0 1 64 150 a [P1-12, P1-25, P1-28] []
1 1 64 150 a [] [P1-25, P1-28, P1-90]
2 1 1000 2000 b [] [P1-89, P1-92, P1-93]
3 1 1000 2000 b [P1-6, P1-89, P1-93] []