2017-01-26 30 views
3

人物の名前(複数のエントリを持つことができます)と2つのカラム 'X'と 'Y'を持つデータフレームがあります。列「X」と「Y」は、A〜Cの間の任意の文字です。 - ボブ私のために一人一人のために各インデックスにpandas groupbyを適用する

df = pd.DataFrame({'X' : ['A', 'B', 'A', 'C'], 'Y' : ['B', 'A', 'A', 'C']},index = ['Bob','Bob','John','Mike']) 

(すなわち、インデックス)、私は例えば、列「X」と「Y」(のすべてのユニークな組み合わせの出現数を取得したいと思います。たとえば

( 'A'、 'B')は1カウント、( 'B'、 'A')は1カウントです。

私は次のようにします。

df.loc['Bob'].groupby(['X','Y']).size() 

私はボブのために正しい結果を得ます。どのようにして、誰もいなくてもこれを行うことができますか? 理想的には、私はインデックスとして、列としての列 'X'と 'Y'のすべてのユニークな組み合わせと、それが値としてデータフレームに現れた回数で、異なる人々とのデータフレームを取得します。

('A','A') ('A','B') ('A','C') ('B','A') ... ('C','C') 
Bob  0   1   0   1    0 
John 1   0   0   0    0 
Mike 0   0   0   0    1 

答えて

3

は、私はあなたが使用することができると思う:

#convert columns X and Y to tuples 
df['tup'] = list(zip(df.X, df.Y)) 

#get size and reshape 
df1 = df.reset_index().groupby(['index','tup']).size().unstack(fill_value=0) 
print (df1) 
tup (A, A) (A, B) (B, A) (C, C) 
index         
Bob   0  1  1  0 
John  1  0  0  0 
Mike  0  0  0  1 

#get all unique combination 
from itertools import product 
comb = list(product(df.X.unique(), df.Y.unique())) 
print (comb) 
[('A', 'B'), ('A', 'A'), ('A', 'C'), ('B', 'B'), ('B', 'A'), 
('B', 'C'), ('C', 'B'), ('C', 'A'), ('C', 'C')] 

#reindex columns by this combination 
print (df1.reindex(columns=comb, fill_value=0)) 
tup (A, B) (A, A) (A, C) (B, B) (B, A) (B, C) (C, B) (C, A) (C, C) 
index                   
Bob   1  0  0  0  1  0  0  0  0 
John  0  1  0  0  0  0  0  0  0 
Mike  0  0  0  0  0  0  0  0  1 
+0

を使用して、pivot_tableでこれを行う方法は、より良い少しありパンダ? –

+0

'pivot_table'を持つソリューションは' df1 = df.reset_index()。pivot_table(index = 'index'、columns = 'tup'、aggfunc = 'size'、fill_value = 0) 'であり、'クロス集計 ' = pd.crosstab(df.index、df.tup) ' – jezrael

4

は、理解のためにget_dummiesgroupby

pd.get_dummies(df.apply(tuple, 1)).groupby(level=0).sum() 

     (A, A) (A, B) (B, A) (C, C) 
Bob  0  1  1  0 
John  1  0  0  0 
Mike  0  0  0  1 
関連する問題