2016-11-27 4 views
4

Ich habe einen Datenrahmen ‚df‘, die wie folgt aussieht:Python Pandas Dataframe GroupBy basiert Größe unter der Bedingung

id date1 date2 
1 11/1/2016 11/1/2016 
1 11/1/2016 11/2/2016 
1 11/1/2016 11/1/2016 
1 11/1/2016 11/2/2016 
1 11/2/2016 11/2/2016 
2 11/1/2016 11/1/2016 
2 11/1/2016 11/2/2016 
2 11/1/2016 11/1/2016 
2 11/2/2016 11/2/2016 
2 11/2/2016 11/2/2016 

Was würde ich tun möchte, ist die ID GROUPBY, dann für jede ID, die Größe, wo Datum1 = Datum2. Das Ergebnis sollte wie folgt aussehen:

id samedate count 
1 11/1/2016 2 
1 11/2/2016 1 
2 11/1/2016 2 
2 11/2/2016 2 

ich dieses versucht haben:

gb=df.groupby(id').apply(lambda x: x[x.date1== x.date2]['date1'].size()) 

Und diesen Fehler:

TypeError: 'int' object is not callable 

Sie sicherlich jede Instanz markieren könnte, wo die date1 und date2 gleich sind , dann zähle diese Flags für jede ID von jedem samedate, aber ich muss glauben, dass es eine groupby-Option dafür gibt.

Antwort

4

gleich können Sie boolean indexing zuerst verwenden und dann Aggregat size:

df.date1 = pd.to_datetime(df.date1) 
df.date2 = pd.to_datetime(df.date2) 

df = df[df.date1 == df.date2] 
gb=df.groupby(['id', 'date1']).size().reset_index(name='count') 
print (gb) 
    id  date1 count 
0 1 2016-11-01  2 
1 1 2016-11-02  1 
2 2 2016-11-01  2 
3 2 2016-11-02  2 

Timings:

In [79]: %timeit (df[df.date1 == df.date2].groupby(['id', 'date1']).size().reset_index(name='count')) 
100 loops, best of 3: 3.84 ms per loop 

In [80]: %timeit (df.groupby(['id', 'date1']).apply(lambda x: (x['date1'] == x['date2']).sum()).reset_index()) 
100 loops, best of 3: 7.57 ms per loop 

-Code für Timings:

#len df = 10k 
df = pd.concat([df]*1000).reset_index(drop=True) 
#print (df) 

df.date1 = pd.to_datetime(df.date1) 
df.date2 = pd.to_datetime(df.date2) 
+0

Danke für die Timings. Dies ist ein besserer Weg, es zu tun. – Zero

+0

Vielen Dank für die Antwort, erste Idee war sehr ähnlich wie Ihre Antwort. – jezrael

+0

Danke. Ausgezeichnet! – clg4

3

Sie müssen sich auf zwei Spalten zu gruppieren und dann prüfen, gelten, wenn date1date2

In [105]: df.groupby(['id', 'date1']).apply(lambda x: (x['date1'] == x['date2']).sum()) 
Out[105]: 
id date1 
1 11/1/2016 2 
    11/2/2016 1 
2 11/1/2016 2 
    11/2/2016 2 
dtype: int64 
+0

Sie wieder gehen langsamer als jezrael sein, wenn Sie die Lambda-Funktion gegen den gesamten Satz anwenden, und wenn Sie den Booleschen Vergleich innerhalb der Lambda-Funktion tun. – Boud

+0

danke für die Antwort. ! – clg4