Ich habe einen großen Datenrahmen, und ich gruppiere von einer bis n Spalten und möchte eine Funktion auf diese Gruppen über zwei Spalten (z. B. foo und bar) anwenden.Wie man groupby über mehrere Spalten transformieren kann
Hier ist ein Beispiel Datenrahmen:
foo_function = lambda x: np.sum(x.a+x.b)
df = pd.DataFrame({'a':[1,2,3,4,5,6],
'b':[1,2,3,4,5,6],
'c':['q', 'q', 'q', 'q', 'w', 'w'],
'd':['z','z','z','o','o','o']})
# works with apply, but I want transform:
df.groupby(['c', 'd'])[['a','b']].apply(foo_function)
# transform doesn't work!
df.groupby(['c', 'd'])[['a','b']].transform(foo_function)
TypeError: cannot concatenate a non-NDFrame object
Aber transform
offenbar nicht in der Lage ist, mehrere Spalten miteinander zu kombinieren, da sie separat in jeder Spalte sehen (im Gegensatz zu rechnen). Was ist die nächstbeste Alternative in Bezug auf Geschwindigkeit/Eleganz? z.B. Ich könnte apply
verwenden und dann df['new_col']
erstellen, indem ich pd.match
benutze, aber das würde die Anpassung über manchmal multiple groupby Spalten (col1 und col2) erfordern, die wirklich hacky scheint/eine ziemlich Menge Code nehmen würde.
-> Gibt es eine Funktion wie groupby(). Transform, die Funktionen verwenden kann, die über mehrere Spalten arbeiten? Wenn das nicht existiert, was ist der beste Hack?
Dies wirft einen Schlüsselfehler in 0.19.1. Es war mein Verständnis, dass die Transformation eine Reihe (jede Spalte) an die Funktion übergibt. Aber seltsamerweise übergibt es auch einmal einen Datenrahmen, wenn das Folgende mit den obigen Daten ausgeführt wird. 'df.groupby (['c', 'd']). transform (lambda x: drucken (type (x)))'.Das sieht wie ein Fehler aus –
@TedPetrou: Danke für das Hinzeigen. Als Leistungsverbesserung könnte "transform" - wie "apply" - versuchen, die Funktion auf (Sub-) Datenrahmen anzuwenden. Unter bestimmten Umständen (z. B. vektorisierte Funktion und viele Spalten) könnte dies schneller sein als die einmalige Anwendung der Funktion für jede Gruppe und Spalte. – unutbu
@TedPetrou: In Bezug auf den 'KeyError' - jetzt, wo ich auf meine ursprüngliche Antwort zurückblicke, glaube ich nicht, dass die von mir vorgeschlagene Lösung eine gute Lösung ist. Die 'Transformation' ruft die Funktion einmal für jede Gruppe auf. Sie erhalten eine bessere Leistung, wenn Sie vektorisierte Funktionen bei größeren Eingaben weniger oft aufrufen. Daher ist es sinnvoller, 'df ['a'] + df ['b']' für die gesamten Spalten * vor dem Aufruf von 'transform' zu berechnen. Ich habe den Beitrag oben geändert, um zu zeigen, was ich meine. – unutbu