2016-05-09 11 views
7

Ich habe derzeit einige Datenmenge, die wie folgt strukturiert:Pandas - Wie gruppieren und entstapeln Sie mehrere Variablen?

data = {'participant': [100, 101, 102, 103, 104, 105, 106, 107, 108, 109], 
     'step_name': ['first', 'first', 'second', 'third', 'second', 'first', 'first', 'first', 'second', 'third'], 
     'title': ['acceptable', 'acceptable', 'not acceptable', 'acceptable', 'not acceptable', 'acceptable', 'not acceptable', 'acceptable', 'acceptable', 'acceptable'], 
     'colour': ['blue', 'blue', 'blue', 'green', 'green', 'blue', 'green', 'blue', 'blue', 'green'], 
     'class': ['A', 'B', 'B', 'A', 'B', 'A', 'A', 'A', 'A', 'B']} 
df = pd.DataFrame(data, columns=['participant', 'step_name', 'title', 'colour', 'class']) 

, die wie folgt aussieht:

+----+---------------+-------------+----------------+----------+---------+ 
| | participant | step_name | title   | colour | class | 
|----+---------------+-------------+----------------+----------+---------| 
| 0 |   100 | first  | acceptable  | blue  | A  | 
| 1 |   101 | first  | acceptable  | blue  | B  | 
| 2 |   102 | second  | not acceptable | blue  | B  | 
| 3 |   103 | third  | acceptable  | green | A  | 
| 4 |   104 | second  | not acceptable | green | B  | 
| 5 |   105 | first  | acceptable  | blue  | A  | 
| 6 |   106 | first  | not acceptable | green | A  | 
| 7 |   107 | first  | acceptable  | blue  | A  | 
| 8 |   108 | second  | acceptable  | blue  | A  | 
| 9 |   109 | third  | acceptable  | green | B  | 
+----+---------------+-------------+----------------+----------+---------+ 

nun den Datensatz Ich möchte aggregieren, so dass jede Zeile jeder der Wiederholungs Variablen zählt, die ich habe zur Zeit geschafft, entlang von zwei Variablen zu tun (step_name und title) wie folgt:

count_df = df[['participant', 'step_name', 'title']].groupby(['step_name', 'title']).count() 
count_df = count_df.unstack() 
count_df.fillna(0, inplace=True) 
count_df.columns = count_df.columns.get_level_values(1) 
count_df 

+--------+--------------+------------------+ 
|  | acceptable | not acceptable | 
|--------+--------------+------------------| 
| first |   4 |    1 | 
| second |   1 |    2 | 
| third |   2 |    0 | 
+--------+--------------+------------------+ 

Nun würde ich gerne eine zusätzliche Reihe von Spalten haben, die die Werte für die anderen Variablen enthält (colour und class) - im Grunde möchte ich gruppieren und dann auf diese Variablen entstapeln, aber bin mir nicht sicher, wie zu tun es mit mehr als 2 Variablen. Letztlich würde Ich mag für meine letzte Tabelle wie folgt aussehen:

+------+------+--------+--------------+------------------+ 
|class |colour| step | acceptable | not acceptable | 
|----------------------+--------------+------------------| 
| A | blue | first |   3 |    0 | 
| B | blue | first |   1 |    0 | 
| A |green | first |   0 |    1 | 
| B |green | first |   0 |    0 | 
| A | blue | second |   1 |    0 | 
| B | blue | second |   0 |    1 | 
| A |green | second |   0 |    0 | 
| B |green | second |   0 |    1 | 
| A |blue | third |   0 |    0 | 
| B |blue | third |   0 |    0 | 
| A |green | third |   1 |    0 | 
| B |green | third |   1 |    0 | 
+------+------+--------+--------------+------------------+ 

Wie kann ich meine Daten neu zu gestalten, so dass es wie mein letztes Beispiel aussieht? Benütze ich noch die Funktionen zum Entstapeln und Gruppieren?

Antwort

5

Ich glaube, Sie brauchen pivot_table mit aggfunc=len, reset_index und rename_axis (neu in pandas0.18.0):

df = df.pivot_table(index=['class','colour','step_name'], 
        columns='title', 
        aggfunc=len, 
        values='participant', 
        fill_value=0).reset_index().rename_axis(None, axis=1) 
print df 
     class colour step_name acceptable not acceptable 
0   A blue  first   3    0 
1   A blue second   1    0 
2   A green  first   0    1 
3   A green  third   1    0 
4   B blue  first   1    0 
5   B blue second   0    1 
6   B green second   0    1 
7   B green  third   1    0 
+0

Dank! Sieht aus wie das 'rename_axis' Bit gibt mir einen Fehler, obwohl -' TypeError: muss einen Index zum Umbenennen übergeben ' – orange1

+1

Es ist eine neue Funktion in 'Pandas 0.18.0', die Sie weglassen können. Und benutze 'df.columns.name = None' – jezrael

6

können Sie pivot_table() für diesen Einsatz:

In [130]: df['count'] = 1 

In [134]: (df.pivot_table(index=['class','colour','step_name'], columns='title', 
    .....:     values='count', aggfunc='sum', fill_value=0) 
    .....: .reset_index() 
    .....:) 
Out[134]: 
title class colour step_name acceptable not acceptable 
0   A blue  first   3    0 
1   A blue second   1    0 
2   A green  first   0    1 
3   A green  third   1    0 
4   B blue  first   1    0 
5   B blue second   0    1 
6   B green second   0    1 
7   B green  third   1    0 
Verwandte Themen