2013-05-16 21 views
7

Chcę scalić dwie ramki danych na określonych kolumnach (klucz1, klucz2) i zsumować wartości dla innej kolumny (wartości).scalanie 2 ramek danych w Pandach: łączenie w niektórych kolumnach, podsumowywanie innych

>>> df1 = pd.DataFrame({'key1': range(4), 'key2': range(4), 'value': range(4)}) 
    key1 key2 value 
0  0  0  0 
1  1  1  1 
2  2  2  2 
3  3  3  3 

>>> df2 = pd.DataFrame({'key1': range(2, 6), 'key2': range(2, 6), 'noise': range(2, 6), 'value': range(10, 14)}) 
    key1 key2 noise value 
0  2  2  2  10 
1  3  3  3  11 
2  4  4  4  12 
3  5  5  5  13 

Chcę ten wynik:

key1 key2 value 
0  0  0  0 
1  1  1  1 
2  2  2  12 
3  3  3  14 
4  4  4  12 
5  5  5  13 

W kategoriach SQL, chcę:

SELECT df1.key1, df1.key2, df1.value + df2.value AS value 
FROM df1 OUTER JOIN df2 ON key1, key2 

Próbowałem dwóch podejść:

podejście 1

concatenated = pd.concat([df1, df2]) 
grouped = concatenated.groupby(['key1', 'key2'], as_index=False) 
summed = grouped.agg(np.sum) 
result = summed[['key1', 'key2', 'value']] 

podejście 2

joined = pd.merge(df1, df2, how='outer', on=['key1', 'key2'], suffixes=['_1', '_2']) 
joined = joined.fillna(0.0) 
joined['value'] = joined['value_1'] + joined['value_2'] 
result = joined[['key1', 'key2', 'value']] 

Oba podejścia daje wynik chcę, ale zastanawiam się, czy istnieje prostszy sposób.

Odpowiedz

8

nie wiem o prostsze, ale można się trochę bardziej zwięzły:

>>> pd.concat([df1, df2]).groupby(["key1", "key2"], as_index=False)["value"].sum() 
    key1 key2 value 
0  0  0  0 
1  1  1  1 
2  2  2  12 
3  3  3  14 
4  4  4  12 
5  5  5  13 

zależności od tolerancji dla łańcuchowym ops, może chcesz przerwać ten na wielu liniach w każdym razie, choć (cztery ma tendencję do zbliżania się do mojego górnego limitu, w tym przypadku concat-groupby-select-sum).

+0

Wygląda na to, że powinny być bardziej zwięzłe ... jak agregacja czasu scalenia. –

+0

Szukałem magicznej funkcji, która robi wszystko w zoptymalizowany sposób. – Laurie

+0

Wybrałem podejście 2, i przykuty ops, jak to możliwe, ponieważ jest szybszy w ten sposób. – Laurie

Powiązane problemy