Wie lösche ich eine Liste von Zeilen aus dem Pandas-Datenrahmen?

258

Ich habe einen Datenrahmen df:

>>> df
                  sales  discount  net_sales    cogs
STK_ID RPT_Date                                     
600141 20060331   2.709       NaN      2.709   2.245
       20060630   6.590       NaN      6.590   5.291
       20060930  10.103       NaN     10.103   7.981
       20061231  15.915       NaN     15.915  12.686
       20070331   3.196       NaN      3.196   2.710
       20070630   7.907       NaN      7.907   6.459

Dann möchte ich Zeilen mit bestimmten Folgenummern löschen, die in einer Liste angegeben sind. Angenommen, hier bleibt [1,2,4],dann Folgendes übrig:

                  sales  discount  net_sales    cogs
STK_ID RPT_Date                                     
600141 20060331   2.709       NaN      2.709   2.245
       20061231  15.915       NaN     15.915  12.686
       20070630   7.907       NaN      7.907   6.459

Wie oder welche Funktion kann das?

großer Käfer
quelle
nur zu klären, ist diese Frage zu Zeilen mit bestimmten Indexwert fallen .. ihre Verwendung von [1,2,4] ist zu Punkt der Zeilen übrig nach Abwurf. Es gibt unten Antworten, die dies tun.
Alchemie

Antworten:

386

Verwenden Sie DataFrame.drop und übergeben Sie ihm eine Reihe von Indexbezeichnungen :

In [65]: df
Out[65]: 
       one  two
one      1    4
two      2    3
three    3    2
four     4    1


In [66]: df.drop(df.index[[1,3]])
Out[66]: 
       one  two
one      1    4
three    3    2
Theodros Zelleke
quelle
18
+1 Zusätzlich, Löschen der letzten Zeile df.drop (df.tail (1) .index)
Nasser Al-Wohaibi
15
Diese Antwort funktioniert nur, wenn df.index.unique () mit df.index identisch ist, was für einen Pandas DataFrame nicht erforderlich ist. Hat jemand eine Lösung, wenn nicht garantiert wird, dass die df.index-Werte eindeutig sind?
J Jones
2
Dies erlaubt Ihnen nicht, auf den
Indexnamen
45
Wenn Sie in Beispielen klar sein möchten, verwenden Sie bitte nicht dieselben Zeichenfolgen für Zeilen und Spalten. Das ist gut für diejenigen, die sich wirklich auskennen. Frustrierend für diejenigen, die versuchen zu lernen.
Gseattle
2
Python-Neulinge: Beachten Sie, dass Sie, wenn Sie diese Zeilen löschen und im selben Datenrahmen (an Ort und Stelle) speichern möchten, auch die axis=0Zeilen (0 = Zeilen, 1 = Spalten) und inplace=Truewie in hinzufügen müssen df.drop(df.index[[1,3]], axis=0, inplace=True). @mezzanaccio, wenn Sie genau wissen, welche Indizes Sie ersetzen möchten (und auch Ihr 0 bis n Beispiel verwenden):df.drop(df.index[range(0, n)], axis=0, inplace=True)
mrbTT
47

Wenn der DataFrame sehr groß ist und auch die Anzahl der zu löschenden Zeilen groß ist, df.drop(df.index[])dauert das einfache Löschen nach Index zu lange.

In meinem Fall habe ich einen mehrfach indizierten DataFrame von Floats mit 100M rows x 3 colsund muss 10kZeilen daraus entfernen . Die schnellste Methode, die ich gefunden habe, ist ziemlich intuitiv zu takeden verbleibenden Zeilen.

Sei indexes_to_dropein Array von Positionsindizes, die gelöscht werden sollen ( [1, 2, 4]in der Frage).

indexes_to_keep = set(range(df.shape[0])) - set(indexes_to_drop)
df_sliced = df.take(list(indexes_to_keep))

In meinem Fall dauerte dies 20.5s, während das Einfache viel Speicher df.dropnahm 5min 27sund verbrauchte. Der resultierende DataFrame ist der gleiche.

Dennis Golomazov
quelle
43

Sie können auch das Label selbst an DataFrame.drop übergeben (anstelle von Serien von Index-Labels):

In[17]: df
Out[17]: 
            a         b         c         d         e
one  0.456558 -2.536432  0.216279 -1.305855 -0.121635
two -1.015127 -0.445133  1.867681  2.179392  0.518801

In[18]: df.drop('one')
Out[18]: 
            a         b         c         d         e
two -1.015127 -0.445133  1.867681  2.179392  0.518801

Welches ist gleichbedeutend mit:

In[19]: df.drop(df.index[[0]])
Out[19]: 
            a         b         c         d         e
two -1.015127 -0.445133  1.867681  2.179392  0.518801
Danielhadar
quelle
1
df.drop (df.index [0]) funktioniert ebenfalls. Ich meine, keine Notwendigkeit für doppelte square_brackets (mit Pandas 0.18.1, mindestens)
Tagoma
23

Ich habe das auf einfachere Weise gelöst - nur in 2 Schritten.

Schritt 1: Bilden Sie zuerst einen Datenrahmen mit unerwünschten Zeilen / Daten.

Schritt 2: Verwenden Sie den Index dieses unerwünschten Datenrahmens, um die Zeilen aus dem ursprünglichen Datenrahmen zu löschen.

Beispiel:

Angenommen, Sie haben einen Datenrahmen df, der so viele Spalten enthält, einschließlich 'Age', das eine Ganzzahl ist. Angenommen, Sie möchten alle Zeilen mit 'Alter' als negativer Zahl löschen.

Schritt 1: df_age_negative = df [df ['Alter'] <0]

Schritt 2: df = df.drop (df_age_negative.index, axis = 0)

Hoffe das ist viel einfacher und hilft dir.

Krishnaprasad Challuru
quelle
1
+1, dies ist die einzige Antwort, die Ihnen sagt, wie Sie eine Zeile entfernen, indem Sie eine andere Spalte als die erste auswählen.
Alejo Bernardin
10

Wenn ich eine Zeile löschen möchte, die beispielsweise einen Index enthält x, würde ich Folgendes tun:

df = df[df.index != x]

Wenn ich mehrere Indizes löschen möchte (sagen wir, diese Indizes sind in der Liste enthalten unwanted_indices), würde ich Folgendes tun:

desired_indices = [i for i in len(df.index) if i not in unwanted_indices]
desired_df = df.iloc[desired_indices]
Divyansh
quelle
6

Hier ist ein etwas spezifisches Beispiel, das ich zeigen möchte. Angenommen, Sie haben viele doppelte Einträge in einigen Ihrer Zeilen. Wenn Sie Zeichenfolgeneinträge haben, können Sie problemlos Zeichenfolgenmethoden verwenden, um alle zu löschenden Indizes zu finden.

ind_drop = df[df['column_of_strings'].apply(lambda x: x.startswith('Keyword'))].index

Und jetzt diese Zeilen mit ihren Indizes löschen

new_df = df.drop(ind_drop)
Cyber-Mathematik
quelle
3

In einem Kommentar zur Antwort von @ theodros-zelleke fragte @ j-jones, was zu tun sei, wenn der Index nicht eindeutig sei. Ich musste mich mit einer solchen Situation auseinandersetzen. Was ich getan habe, war, die Duplikate im Index umzubenennen, bevor ich aufgerufen habe drop(), a la:

dropped_indexes = <determine-indexes-to-drop>
df.index = rename_duplicates(df.index)
df.drop(df.index[dropped_indexes], inplace=True)

Wo rename_duplicates()ist eine von mir definierte Funktion, die die Elemente des Index durchlief und die Duplikate umbenannte? Ich habe das gleiche Umbenennungsmuster pd.read_csv()verwendet wie für Spalten, dh "%s.%d" % (name, count)wo nameist der Name der Zeile und countwie oft sie zuvor aufgetreten ist.

Mepstein
quelle
1

Bestimmen des Index aus dem Booleschen Wert wie oben beschrieben, z

df[df['column'].isin(values)].index

kann speicherintensiver sein als das Bestimmen des Index mit dieser Methode

pd.Index(np.where(df['column'].isin(values))[0])

so angewendet

df.drop(pd.Index(np.where(df['column'].isin(values))[0]), inplace = True)

Diese Methode ist nützlich, wenn Sie mit großen Datenrahmen und begrenztem Speicher arbeiten.

Adam Zeldin
quelle
0

Verwenden Sie nur das Index-Argument, um die Zeile zu löschen: -

df.drop(index = 2, inplace = True)

Für mehrere Zeilen: -

df.drop(index=[1,3], inplace = True)
Kamran Kausar
quelle
0

Betrachten Sie einen beispielhaften Datenrahmen

df =     
index    column1
0           00
1           10
2           20
3           30

Wir wollen die 2. und 3. Indexzeile löschen.

Ansatz 1:

df = df.drop(df.index[2,3])
 or 
df.drop(df.index[2,3],inplace=True)
print(df)

df =     
index    column1
0           00
3           30

 #This approach removes the rows as we wanted but the index remains unordered

Ansatz 2

df.drop(df.index[2,3],inplace=True,ignore_index=True)
print(df)
df =     
index    column1
0           00
1           30
#This approach removes the rows as we wanted and resets the index. 
Festland
quelle