我得到了一個(pandas)資料框,告訴我關于人和俱樂部的會員關系。我想找到的是任何兩個俱樂部的共同成員數量。
示例輸入:
Person Club
1 A
1 B
1 C
2 A
2 C
3 A
3 B
4 C
換句話說,A = {1,2,3},B = {1,3},C = {1,2,4}。
期望的輸出:
Club 1 Club 2 Num_Overlaps
A B 1
A C 2
B C 1
我當然可以撰寫計算這些數字的 python 代碼,但我想必須有一種使用 groupby 左右的更接近資料幀的方式來完成相同的任務。
uj5u.com熱心網友回復:
首先,我將俱樂部上的資料框分組以獲得俱樂部中每個人的一組資料。
grouped = df.groupby("Club").agg({"Person": set}).reset_index()
Club Person
0 A {1, 2, 3}
1 B {1, 3}
2 C {1, 2, 4}
然后,我創建了這個資料框的笛卡爾積。我沒有 Pandas 1.2.0,所以我無法使用df.merge(). 相反,我使用了這個答案的想法:pandas two dataframe cross join
grouped["key"] = 0
product = grouped.merge(grouped, on="key", how="outer").drop(columns="key")
Club_x Person_x Club_y Person_y
0 A {1, 2, 3} A {1, 2, 3}
1 A {1, 2, 3} B {1, 3}
2 A {1, 2, 3} C {1, 2, 4}
3 B {1, 3} A {1, 2, 3}
4 B {1, 3} B {1, 3}
5 B {1, 3} C {1, 2, 4}
6 C {1, 2, 4} A {1, 2, 3}
7 C {1, 2, 4} B {1, 3}
8 C {1, 2, 4} C {1, 2, 4}
然后我過濾掉了對的地方,Club_x < Club_y以便洗掉重復的對。
filtered = product[product["Club_x"] < product["Club_y"]]
Club_x Person_x Club_y Person_y
1 A {1, 2, 3} B {1, 3}
2 A {1, 2, 3} C {1, 2, 4}
5 B {1, 3} C {1, 2, 4}
最后,我添加了具有重疊大小的列,并根據需要重命名了列。
result = filtered.assign(Num_Overlaps=filtered.apply(lambda row: len(row["Person_x"].intersection(row["Person_y"])), axis=1))
result = result.rename(columns={"Club_x": "Club 1", "Club_y": "Club 2"}).drop(["Person_x", "Person_y"], axis=1)
Club 1 Club 2 Num_Overlaps
1 A B 2
2 A C 2
5 B C 1
uj5u.com熱心網友回復:
你確實可以通過groupby一些設定操作來做到這一點。我還會使用itertools.combinations, 來獲取俱樂部對的串列。
import pandas as pd
from itertools import combinations
df = pd.DataFrame({'Person': [1, 1, 1, 2, 2, 3, 3, 4],
'Club': list('ABCACABC')})
members = df.groupby('Club').agg(set)
clubs = sorted(list(set(df.Club)))
overlap = pd.DataFrame(list(combinations(clubs, 2)),
columns=['Club 1', 'Club 2'])
def n_overlap(row):
club1, club2 = row
members1 = members.loc[club1, 'Person']
members2 = members.loc[club2, 'Person']
return len(members1.intersection(members2))
overlap['Num_Overlaps'] = overlap.apply(n_overlap, axis=1)
overlap
Club 1 Club 2 Num_Overlaps
0 A B 2
1 A C 2
2 B C 1
請注意,您想要的輸出有一個區別,但這可能是應該的,正如@rchome 在上面的評論中所指出的那樣。
轉載請註明出處,本文鏈接:https://www.uj5u.com/shujuku/383536.html
