2014-07-09 11 views
5

Wyobraź sobie, że mam DataFrame z kolumnami zawierającymi tylko rzeczywiste wartości.Grupuj podane percentyle wartości wybranej kolumny DataFrame

>> df   
      col1 col2  col3 
0  0.907609  82 4.207991 
1  3.743659 1523 6.488842 
2  2.358696 324 5.092592 
3  0.006793  0 0.000000 
4 19.319746 11969 7.405685 

I pogrupować jej przez kwartyli (lub innych percentyli określonych Me) wybranego kolumnie (np col1) do wykonywania pewnych operacji na tych grupach. Idealnie, chciałbym zrobić coś takiego:

df.groupy(quartiles_of_col1).mean() # not working, how to code quartiles_of_col1? 

Wyjście powinno dać średnią z każdej z kolumn dla czterech grup odpowiadających kwartyla col1. Czy jest to możliwe przy użyciu polecenia groupby? Jaki jest najprostszy sposób na osiągnięcie tego?

Odpowiedz

7

nie mam komputera w celu przetestowania go teraz, ale myślę, że można to zrobić przez : df.groupby(pd.cut(df.col0, np.percentile(df.col0, [0, 25, 75, 90, 100]), include_lowest=True)).mean(). Aktualizacja po 150 minutach.

Niektóre wyjaśnienia:

In [42]: 
#use np.percentile to get the bin edges of any percentile you want 
np.percentile(df.col0, [0, 25, 75, 90, 100]) 
Out[42]: 
[0.0067930000000000004, 
0.907609, 
3.7436589999999996, 
13.089311200000001, 
19.319745999999999] 
In [43]: 
#Need to use include_lowest=True 
print df.groupby(pd.cut(df.col0, np.percentile(df.col0, [0, 25, 75, 90, 100]), include_lowest=True)).mean() 
         col0  col1  col2 
col0           
[0.00679, 0.908] 0.457201  41.0 2.103996 
(0.908, 3.744]  3.051177 923.5 5.790717 
(3.744, 13.0893]  NaN  NaN  NaN 
(13.0893, 19.32] 19.319746 11969.0 7.405685 
In [44]: 
#Or the smallest values will be skiped 
print df.groupby(pd.cut(df.col0, np.percentile(df.col0, [0, 25, 75, 90, 100]))).mean() 
         col0  col1  col2 
col0           
(0.00679, 0.908] 0.907609  82.0 4.207991 
(0.908, 3.744]  3.051177 923.5 5.790717 
(3.744, 13.0893]  NaN  NaN  NaN 
(13.0893, 19.32] 19.319746 11969.0 7.405685 
+2

To działa dla mnie! Doskonałe wykorzystanie cięcia! Podzięka za championa – biobirdman

+1

Przykład dodany. Okazuje się, że chcesz ustawić 'include_lowest' na 'True', w przeciwnym razie najmniejsze numery zostaną pominięte. Edytowane. Twoje zdrowie! –

0

Mam nadzieję, że rozwiąże to Twój problem. To nie jest ładne, ale mam nadzieję, że będzie pracować dla Ciebie

import pandas as pd 
    import random 
    import numpy as np 
    ## create a mock df as example. with column A, B, C and D 
    df = pd.DataFrame(np.random.randn(100, 4), columns=list('ABCD')) 

    ## select dataframe based on the quantile of column A, using the quantile method. 
    df[df['A'] < df['A'].quantile(0.3)].mean() 

to wypisze

A -1.157615 
B 0.205529 
C -0.108263 
D 0.346752 
dtype: float64 
+0

dobrze, to jest ok dla jednej percentyla, ale ja specjalnie poszukiwania dla rozwiązania, które uzyska "średnią" dla każdej z grup zdefiniowanych przez kwantyle/q-kwantyle. – pms

+0

Co powiesz na wykonanie pętli for, która zastąpi wartość kwantylu? – biobirdman

+0

Tak, jest to możliwe, ale nie jest eleganckie ani wydajne. Wyobraź sobie, że masz duży współczynnik DF i chcesz podzielić go na 10-cuantyli. Wykonanie pętli oznaczałoby, że idziesz 10 razy ponad DF, aby zgrupować dane. – pms