Spalten in Pandas umbenennen

1824

Ich habe einen DataFrame mit Pandas und Spaltenbeschriftungen, die ich bearbeiten muss, um die ursprünglichen Spaltenbeschriftungen zu ersetzen.

Ich möchte die Spaltennamen in einem DataFrame ändern, Awobei die ursprünglichen Spaltennamen lauten:

['$a', '$b', '$c', '$d', '$e'] 

zu

['a', 'b', 'c', 'd', 'e'].

Ich habe die bearbeiteten Spaltennamen in einer Liste gespeichert, weiß aber nicht, wie ich die Spaltennamen ersetzen soll.

user1504276
quelle
1
Vielleicht möchten Sie die offiziellen Dokumente lesen
ccpizza

Antworten:

1828

Weisen Sie es einfach dem .columnsAttribut zu:

>>> df = pd.DataFrame({'$a':[1,2], '$b': [10,20]})
>>> df.columns = ['a', 'b']
>>> df
   a   b
0  1  10
1  2  20
Eumiro
quelle
303
Ist es möglich, einen einzelnen Spaltenkopfnamen zu ändern?
Ericmjl
112
@ericmjl: Angenommen, Sie möchten den Namen der ersten Variablen von df ändern. Dann können Sie etwas tun wie:new_columns = df.columns.values; new_columns[0] = 'XX'; df.columns = new_columns
CD98
54
Sieht so aus, als hättest du einfach df.columns.values ​​[0] = 'XX'
RAY
25
Nur ein Scherz, @RAY - tu das nicht. Es sieht so aus, als wäre dies eine Liste, die unabhängig davon generiert wird, in welcher Indizierung der Spaltenname gespeichert ist. Macht einen guten Job und zerstört die Spaltenbenennung für Ihren df ...
Mitch Flax
433
@ericmjl jadf.rename(columns = {'$b':'B'}, inplace = True)
Nachocab
2846

SPEZIFISCHE SPALTEN UMBENENNEN

Verwenden Sie die df.rename()Funktion und verweisen Sie auf die umzubenennenden Spalten. Nicht alle Spalten müssen umbenannt werden:

df = df.rename(columns={'oldName1': 'newName1', 'oldName2': 'newName2'})
# Or rename the existing DataFrame (rather than creating a copy) 
df.rename(columns={'oldName1': 'newName1', 'oldName2': 'newName2'}, inplace=True)

Minimales Codebeispiel

df = pd.DataFrame('x', index=range(3), columns=list('abcde'))
df

   a  b  c  d  e
0  x  x  x  x  x
1  x  x  x  x  x
2  x  x  x  x  x

Die folgenden Methoden funktionieren alle und erzeugen dieselbe Ausgabe:

df2 = df.rename({'a': 'X', 'b': 'Y'}, axis=1)  # new method
df2 = df.rename({'a': 'X', 'b': 'Y'}, axis='columns')
df2 = df.rename(columns={'a': 'X', 'b': 'Y'})  # old method  

df2

   X  Y  c  d  e
0  x  x  x  x  x
1  x  x  x  x  x
2  x  x  x  x  x

Denken Sie daran, das Ergebnis zurück zuzuweisen, da die Änderung nicht vorhanden ist. Alternativ geben Sie Folgendes an inplace=True:

df.rename({'a': 'X', 'b': 'Y'}, axis=1, inplace=True)
df

   X  Y  c  d  e
0  x  x  x  x  x
1  x  x  x  x  x
2  x  x  x  x  x

Ab Version 0.25 können Sie auch angeben errors='raise', dass Fehler ausgelöst werden sollen, wenn eine ungültige Spalte zum Umbenennen angegeben wird. Siehe v0.25- rename()Dokumente .


SPALTENKOPF neu zuordnen

Verwenden Sie df.set_axis()mit axis=1und inplace=False(um eine Kopie zurückzugeben).

df2 = df.set_axis(['V', 'W', 'X', 'Y', 'Z'], axis=1, inplace=False)
df2

   V  W  X  Y  Z
0  x  x  x  x  x
1  x  x  x  x  x
2  x  x  x  x  x

Dies gibt eine Kopie zurück, aber Sie können den DataFrame direkt durch Festlegen ändern inplace=True (dies ist das Standardverhalten für Versionen <= 0,24, wird sich aber wahrscheinlich in Zukunft ändern).

Sie können Header auch direkt zuweisen:

df.columns = ['V', 'W', 'X', 'Y', 'Z']
df

   V  W  X  Y  Z
0  x  x  x  x  x
1  x  x  x  x  x
2  x  x  x  x  x
lexuell
quelle
2
wenn ich das mit einem 6 Spaltendatenrahmen (Datenrahmen <drücken Sie die Eingabetaste>) die abgekürzte Darstellung: code<class 'pandas.core.frame.DataFrame> Int64Index: 1000 Einträge, 0 bis 999 Datenspalten: BodyMarkdown 1000 Nicht-Null - codeWerke , aber wenn ich dataframe.head () mache, erscheinen die alten Namen für die Spalten wieder.
DarKoram
12
Ich werde gefürchtet, SettingWithCopyWarning:wenn ich das zweite Code-Snippet in dieser Antwort verwende.
Monica Heddneck
Gibt es eine Version davon mit Regex-Ersatz?
Denfromufa
@lexual Was ist, wenn zwei vorhandene Spalten denselben Namen haben? Wie beziehe ich mich auf den alten Spaltennamen?
Vagabund
14
Die erste Lösung: df = df.rename(columns={'oldName1': 'newName1', 'oldName2': 'newName2'})Ändert den angezeigten Namen, jedoch nicht die Elemente in der zugrunde liegenden Datenstruktur. Wenn Sie es also versuchen df['newName1'], wird eine Fehlermeldung angezeigt. Das inplace=Trueist notwendig, um diese Gotchya zu vermeiden.
irritable_phd_syndrom
402

Die renameMethode kann eine Funktion annehmen , zum Beispiel:

In [11]: df.columns
Out[11]: Index([u'$a', u'$b', u'$c', u'$d', u'$e'], dtype=object)

In [12]: df.rename(columns=lambda x: x[1:], inplace=True)

In [13]: df.columns
Out[13]: Index([u'a', u'b', u'c', u'd', u'e'], dtype=object)
Andy Hayden
quelle
56
Nett. Dieser rettete meinen Tag:df.rename(columns=lambda x: x.lstrip(), inplace=True)
root-11
2
Ähnlich wie bei @ root-11 gab es in meinem Fall ein Aufzählungszeichen, das nicht in der IPython-Konsolenausgabe gedruckt wurde. Daher musste ich mehr als nur Leerzeichen (Streifen) entfernen, also:t.columns = t.columns.str.replace(r'[^\x00-\x7F]+','')
The Red Pea
9
df.rename(columns=lambda x: x.replace(' ', '_'), inplace=True)ist ein Juwel, damit wir schreiben können, df.Column_1_Nameanstatt zu schreiben df.loc[:, 'Column 1 Name'].
Little Bobby Tables
179

Wie in Arbeiten mit Textdaten dokumentiert :

df.columns = df.columns.str.replace('$','')
Kadee
quelle
163

Pandas 0.21+ Antwort

In Version 0.21 wurden einige wichtige Aktualisierungen für das Umbenennen von Spalten vorgenommen.

  • Die renameMethode hat den axisParameter hinzugefügt, der auf columnsoder gesetzt werden kann 1. Durch dieses Update stimmt diese Methode mit dem Rest der Pandas-API überein. Es hat immer noch die Parameter indexund columns, aber Sie sind nicht mehr gezwungen, sie zu verwenden.
  • Mit der set_axisMethode mit der inplaceEinstellung auf Falsekönnen Sie alle Index- oder Spaltenbezeichnungen mit einer Liste umbenennen.

Beispiele für Pandas 0.21+

Erstellen Sie einen Beispiel-DataFrame:

df = pd.DataFrame({'$a':[1,2], '$b': [3,4], 
                   '$c':[5,6], '$d':[7,8], 
                   '$e':[9,10]})

   $a  $b  $c  $d  $e
0   1   3   5   7   9
1   2   4   6   8  10

Verwenden renamemit axis='columns'oderaxis=1

df.rename({'$a':'a', '$b':'b', '$c':'c', '$d':'d', '$e':'e'}, axis='columns')

oder

df.rename({'$a':'a', '$b':'b', '$c':'c', '$d':'d', '$e':'e'}, axis=1)

Beides führt zu Folgendem:

   a  b  c  d   e
0  1  3  5  7   9
1  2  4  6  8  10

Es ist weiterhin möglich, die alte Methodensignatur zu verwenden:

df.rename(columns={'$a':'a', '$b':'b', '$c':'c', '$d':'d', '$e':'e'})

Die renameFunktion akzeptiert auch Funktionen, die auf jeden Spaltennamen angewendet werden.

df.rename(lambda x: x[1:], axis='columns')

oder

df.rename(lambda x: x[1:], axis=1)

Verwenden set_axismit einer Liste undinplace=False

Sie können der set_axisMethode eine Liste bereitstellen, deren Länge der Anzahl der Spalten (oder des Index) entspricht. Derzeit inplacestandardmäßig True, sondern inplacewird vorbelegt werden FalseMeldungen in der Zukunft.

df.set_axis(['a', 'b', 'c', 'd', 'e'], axis='columns', inplace=False)

oder

df.set_axis(['a', 'b', 'c', 'd', 'e'], axis=1, inplace=False)

Warum nicht verwenden df.columns = ['a', 'b', 'c', 'd', 'e']?

Es ist nichts Falsches daran, Spalten direkt so zuzuweisen. Es ist eine vollkommen gute Lösung.

Der Vorteil der Verwendung set_axisbesteht darin, dass sie als Teil einer Methodenkette verwendet werden kann und eine neue Kopie des DataFrame zurückgibt. Ohne sie müssten Sie Ihre Zwischenschritte der Kette in einer anderen Variablen speichern, bevor Sie die Spalten neu zuweisen.

# new for pandas 0.21+
df.some_method1()
  .some_method2()
  .set_axis()
  .some_method3()

# old way
df1 = df.some_method1()
        .some_method2()
df1.columns = columns
df1.some_method3()
Ted Petrou
quelle
1
Vielen Dank für die Pandas 0.21+ answer- irgendwie habe ich diesen Teil im "Was ist neu" Teil verpasst ...
MaxU
1
Die Lösung scheint für Pandas 3.6 nicht zu funktionieren: df.rename ({'$ a': 'a', '$ b': 'b', '$ c': 'c', '$ d': 'd ',' $ e ':' e '}, Achse =' Spalten '). Ruft ein unerwartetes Schlüsselwortargument "Achse" ab
Arthur D. Howland
3
df.columns = ['a', 'b', 'c', 'd', 'e'] scheint nicht mehr zu funktionieren, funktioniert mit Version 0.22 Ich habe eine Warnung, dass Pandas nicht zulässt, dass Spalten über erstellt werden ein neuer Attributname . Wie benenne ich um, wenn alle meine Spalten gleich heißen: /
Nabla
Gibt es eine Möglichkeit, eine, mehrere oder alle Spalten umzubenennen, wenn Sie den Namen der Spalte (n) vorher nicht kennen, sondern nur deren Index? Vielen Dank!
Tommy.carstensen
Dies war ein sehr hilfreicher Kommentar. Zum Beispiel beantwortete die Lambda-Funktion meine Frage, wie man Folgendes macht:(df .groupby(['page',pd.Grouper(key='date',freq='MS')])['clicks'].sum() .unstack(1) .rename(lambda x: x.strftime("%Y-%m"), axis='columns') )
Messen Sie
131

Da Sie nur das $ -Zeichen in allen Spaltennamen entfernen möchten, können Sie Folgendes tun:

df = df.rename(columns=lambda x: x.replace('$', ''))

ODER

df.rename(columns=lambda x: x.replace('$', ''), inplace=True)
paulo.filip3
quelle
1
Dieser hilft nicht nur bei OP, sondern auch bei allgemeinen Anforderungen. Beispiel: Teilen Sie einen Spaltennamen durch ein Trennzeichen und verwenden Sie einen Teil davon.
Deepak
77
df.columns = ['a', 'b', 'c', 'd', 'e']

Die vorhandenen Namen werden in der von Ihnen angegebenen Reihenfolge durch die von Ihnen angegebenen Namen ersetzt.

M PAUL
quelle
5
Nicht ändern df.columns.values, das ist falsch. stackoverflow.com/questions/43291781/…
llllllllll
61
old_names = ['$a', '$b', '$c', '$d', '$e'] 
new_names = ['a', 'b', 'c', 'd', 'e']
df.rename(columns=dict(zip(old_names, new_names)), inplace=True)

Auf diese Weise können Sie das manuell bearbeiten, new_nameswie Sie möchten. Funktioniert hervorragend, wenn Sie nur wenige Spalten umbenennen müssen, um Rechtschreibfehler, Akzente, Sonderzeichen usw. zu korrigieren.

Migloo
quelle
1
Ich mag diesen Ansatz, aber ich denke, df.columns = ['a', 'b', 'c', 'd', 'e']ist einfacher.
Christopher Pearson
1
Ich mag diese Methode, alte und neue Namen zu komprimieren. Wir können verwenden df.columns.values, um die alten Namen zu bekommen.
Bkowshik
1
Ich zeige die tabellarische Ansicht an und kopiere die Spalten in old_names. Ich kopiere das Anforderungsarray nach new_names. Verwenden Sie dann dict (zip (old_names, new_names)). Sehr elegante Lösung.
mythicalcoder
Ich verwende oft Teilmengen von Listen von: myList = list(df) myList[10:20]usw. - das ist also perfekt.
Tim Gottgetreu
Nehmen Sie am besten die alten Namen wie von @bkowshik vorgeschlagen, bearbeiten Sie sie und fügen Sie sie erneut ein, dh namez = df.columns.valuesgefolgt von einigen Änderungen df.columns = namez.
Pauljohn32
34

Einzeilige oder Pipeline-Lösungen

Ich werde mich auf zwei Dinge konzentrieren:

  1. OP stellt klar fest

    Ich habe die bearbeiteten Spaltennamen in einer Liste gespeichert, weiß aber nicht, wie ich die Spaltennamen ersetzen soll.

    Ich möchte nicht das Problem lösen, wie '$'das erste Zeichen aus jeder Spaltenüberschrift ersetzt oder entfernt werden kann. OP hat diesen Schritt bereits ausgeführt. Stattdessen möchte ich mich darauf konzentrieren, das vorhandene columnsObjekt durch ein neues zu ersetzen, wenn eine Liste mit Ersatzspaltennamen vorhanden ist.

  2. df.columns = newWo newist die Liste der neuen Spaltennamen ist so einfach wie es nur geht. Der Nachteil dieses Ansatzes besteht darin, dass das columnsAttribut des vorhandenen Datenrahmens bearbeitet werden muss und nicht inline ausgeführt wird. Ich werde einige Möglichkeiten zeigen, wie dies per Pipelining durchgeführt werden kann, ohne den vorhandenen Datenrahmen zu bearbeiten.


Setup 1
Um sich auf die Notwendigkeit zu konzentrieren, Spaltennamen durch eine bereits vorhandene Liste zu ersetzen, erstelle ich einen neuen Beispieldatenrahmen dfmit anfänglichen Spaltennamen und nicht verwandten neuen Spaltennamen.

df = pd.DataFrame({'Jack': [1, 2], 'Mahesh': [3, 4], 'Xin': [5, 6]})
new = ['x098', 'y765', 'z432']

df

   Jack  Mahesh  Xin
0     1       3    5
1     2       4    6

Lösung 1
pd.DataFrame.rename

Es ist gesagt worden , dass bereits , wenn Sie ein Wörterbuch - Mapping der alten Spaltennamen an den neuen Spaltennamen haben, konnte man verwenden pd.DataFrame.rename.

d = {'Jack': 'x098', 'Mahesh': 'y765', 'Xin': 'z432'}
df.rename(columns=d)

   x098  y765  z432
0     1     3     5
1     2     4     6

Sie können dieses Wörterbuch jedoch einfach erstellen und in den Aufruf von aufnehmen rename. Im Folgenden wird die Tatsache ausgenutzt, dass beim Iterieren dfjeder Spaltenname durchlaufen wird.

# given just a list of new column names
df.rename(columns=dict(zip(df, new)))

   x098  y765  z432
0     1     3     5
1     2     4     6

Dies funktioniert hervorragend, wenn Ihre ursprünglichen Spaltennamen eindeutig sind. Wenn dies nicht der Fall ist, bricht dies zusammen.


Richten Sie 2
nicht eindeutige Spalten ein

df = pd.DataFrame(
    [[1, 3, 5], [2, 4, 6]],
    columns=['Mahesh', 'Mahesh', 'Xin']
)
new = ['x098', 'y765', 'z432']

df

   Mahesh  Mahesh  Xin
0       1       3    5
1       2       4    6

Lösung 2
pd.concat mit dem keysArgument

Beachten Sie zunächst, was passiert, wenn wir versuchen, Lösung 1 zu verwenden:

df.rename(columns=dict(zip(df, new)))

   y765  y765  z432
0     1     3     5
1     2     4     6

Wir haben die newListe nicht als Spaltennamen zugeordnet. Wir haben uns wiederholt y765. Stattdessen können wir das keysArgument der pd.concatFunktion verwenden, während wir durch die Spalten von iterieren df.

pd.concat([c for _, c in df.items()], axis=1, keys=new) 

   x098  y765  z432
0     1     3     5
1     2     4     6

Lösung 3
Rekonstruieren. Dies sollte nur verwendet werden, wenn Sie dtypefür alle Spalten eine einzige haben . Andernfalls erhalten Sie dtype objectalle Spalten, und das Zurückkonvertieren erfordert mehr Wörterbucharbeit.

Single dtype

pd.DataFrame(df.values, df.index, new)

   x098  y765  z432
0     1     3     5
1     2     4     6

Gemischt dtype

pd.DataFrame(df.values, df.index, new).astype(dict(zip(new, df.dtypes)))

   x098  y765  z432
0     1     3     5
1     2     4     6

Lösung 4
Dies ist ein kniffliger Trick mit transposeund set_index. pd.DataFrame.set_indexermöglicht es uns, einen Index inline zu setzen, aber es gibt keine entsprechenden set_columns. Wir können also transponieren set_indexund zurück transponieren. Allerdings ist die gleiche Single im dtypeVergleich zu gemischtem dtypegilt Vorbehalt aus der Lösung 3 hier.

Single dtype

df.T.set_index(np.asarray(new)).T

   x098  y765  z432
0     1     3     5
1     2     4     6

Gemischt dtype

df.T.set_index(np.asarray(new)).T.astype(dict(zip(new, df.dtypes)))

   x098  y765  z432
0     1     3     5
1     2     4     6

Lösung 5
Verwenden Sie ein lambdaIn pd.DataFrame.rename, das jedes Element von durchläuft. new
In dieser Lösung übergeben wir ein Lambda, das es nimmt x, es dann aber ignoriert. Es dauert auch ein y, aber erwartet es nicht. Stattdessen wird ein Iterator als Standardwert angegeben, und ich kann diesen dann verwenden, um einen nach dem anderen zu durchlaufen, ohne Rücksicht auf den Wert von x.

df.rename(columns=lambda x, y=iter(new): next(y))

   x098  y765  z432
0     1     3     5
1     2     4     6

Und wie mir die Leute im Sopython- Chat gesagt haben , kann ich meine Variable schützen , wenn ich *dazwischen ein xund hinzufüge . In diesem Zusammenhang glaube ich jedoch nicht, dass es geschützt werden muss. Es ist immer noch erwähnenswert.yy

df.rename(columns=lambda x, *, y=iter(new): next(y))

   x098  y765  z432
0     1     3     5
1     2     4     6
piRSquared
quelle
Vielleicht können wir hinzufügendf.rename(lambda x : x.lstrip('$'),axis=1)
YOBEN_S
Hallo @piRSquared, könnten Sie bitte erläutern, wie Pandas die Lambda-Funktion in Lösung 5 verwendet? Ich folge nicht ganz dem, was du meinst, wenn du sagst, dass xes ignoriert wird?
Josmoor98
33

Spaltennamen vs Seriennamen

Ich möchte ein wenig erklären, was hinter den Kulissen passiert.

Datenrahmen sind eine Reihe von Serien.

Serien wiederum sind eine Erweiterung von a numpy.array

numpy.arrays haben eine Eigenschaft .name

Dies ist der Name der Serie. Es ist selten, dass Pandas dieses Attribut respektieren, aber es verweilt an einigen Stellen und kann verwendet werden, um einige Pandas-Verhaltensweisen zu hacken.

Benennen der Spaltenliste

Viele Antworten sprechen hier davon, dass das df.columnsAttribut ein ist, listobwohl es tatsächlich ein ist Series. Dies bedeutet, dass es ein .nameAttribut hat.

Dies passiert, wenn Sie den Namen der Spalten eingeben Series:

df.columns = ['column_one', 'column_two']
df.columns.names = ['name of the list of columns']
df.index.names = ['name of the index']

name of the list of columns     column_one  column_two
name of the index       
0                                    4           1
1                                    5           2
2                                    6           3

Beachten Sie, dass der Name des Index immer eine Spalte tiefer steht.

Verweilende Artefakte

Das .nameAttribut bleibt manchmal bestehen. Wenn Sie df.columns = ['one', 'two']dann df.one.nameeinstellen, wird das sein 'one'.

Wenn Sie df.one.name = 'three'dann setzen, df.columnswird Ihnen immer noch geben ['one', 'two'], und df.one.namewird Ihnen geben'three'

ABER

pd.DataFrame(df.one) wird zurückkehren

    three
0       1
1       2
2       3

Weil Pandas .namedas bereits Definierte wiederverwenden Series.

Mehrstufige Spaltennamen

Pandas hat Möglichkeiten, mehrschichtige Spaltennamen zu erstellen. Es geht nicht so sehr um Magie, aber ich wollte dies auch in meiner Antwort behandeln, da ich hier niemanden sehe, der dies aufgreift.

    |one            |
    |one      |two  |
0   |  4      |  1  |
1   |  5      |  2  |
2   |  6      |  3  |

Dies ist leicht zu erreichen, indem Spalten wie folgt auf Listen gesetzt werden:

df.columns = [['one', 'one'], ['one', 'two']]
Firelynx
quelle
18

Wenn Sie den Datenrahmen haben, speichert df.columns alles in einer Liste, die Sie bearbeiten und dann als Namen von Spalten in Ihrem Datenrahmen neu zuweisen können ...

columns = df.columns
columns = [row.replace("$","") for row in columns]
df.rename(columns=dict(zip(columns, things)), inplace=True)
df.head() #to validate the output

Bester Weg? IDK. Ein Weg - ja.

Eine bessere Methode zur Bewertung aller Haupttechniken, die in den Antworten auf die Frage aufgeführt sind, ist die Verwendung von cProfile zur Messung des Speichers und der Ausführungszeit. @kadee, @kaitlyn & @eumiro hatten die Funktionen mit den schnellsten Ausführungszeiten - obwohl diese Funktionen so schnell sind, vergleichen wir die Rundung von .000 und .001 Sekunden für alle Antworten. Moral: Meine Antwort oben ist wahrscheinlich nicht der beste Weg.

import pandas as pd
import cProfile, pstats, re

old_names = ['$a', '$b', '$c', '$d', '$e']
new_names = ['a', 'b', 'c', 'd', 'e']
col_dict = {'$a': 'a', '$b': 'b','$c':'c','$d':'d','$e':'e'}

df = pd.DataFrame({'$a':[1,2], '$b': [10,20],'$c':['bleep','blorp'],'$d':[1,2],'$e':['texa$','']})

df.head()

def eumiro(df,nn):
    df.columns = nn
    #This direct renaming approach is duplicated in methodology in several other answers: 
    return df

def lexual1(df):
    return df.rename(columns=col_dict)

def lexual2(df,col_dict):
    return df.rename(columns=col_dict, inplace=True)

def Panda_Master_Hayden(df):
    return df.rename(columns=lambda x: x[1:], inplace=True)

def paulo1(df):
    return df.rename(columns=lambda x: x.replace('$', ''))

def paulo2(df):
    return df.rename(columns=lambda x: x.replace('$', ''), inplace=True)

def migloo(df,on,nn):
    return df.rename(columns=dict(zip(on, nn)), inplace=True)

def kadee(df):
    return df.columns.str.replace('$','')

def awo(df):
    columns = df.columns
    columns = [row.replace("$","") for row in columns]
    return df.rename(columns=dict(zip(columns, '')), inplace=True)

def kaitlyn(df):
    df.columns = [col.strip('$') for col in df.columns]
    return df

print 'eumiro'
cProfile.run('eumiro(df,new_names)')
print 'lexual1'
cProfile.run('lexual1(df)')
print 'lexual2'
cProfile.run('lexual2(df,col_dict)')
print 'andy hayden'
cProfile.run('Panda_Master_Hayden(df)')
print 'paulo1'
cProfile.run('paulo1(df)')
print 'paulo2'
cProfile.run('paulo2(df)')
print 'migloo'
cProfile.run('migloo(df,old_names,new_names)')
print 'kadee'
cProfile.run('kadee(df)')
print 'awo'
cProfile.run('awo(df)')
print 'kaitlyn'
cProfile.run('kaitlyn(df)')
andrewwowens
quelle
Warum benötigen Sie eine Umbenennungsmethode? So etwas hat bei mir funktioniert # df.columns = [row.replace ('$', '') für row in df.columns]
shantanuo
Ich verstehe den Teil "Dinge" nicht. Was muss ich ersetzen? Die alten Säulen?
Andrea Ianni ௫
18

Angenommen, dies ist Ihr Datenrahmen.

Geben Sie hier die Bildbeschreibung ein

Sie können die Spalten mit zwei Methoden umbenennen.

  1. Verwenden von dataframe.columns=[#list]

    df.columns=['a','b','c','d','e']

    Geben Sie hier die Bildbeschreibung ein

    Die Einschränkung dieser Methode besteht darin, dass, wenn eine Spalte geändert werden muss, die vollständige Spaltenliste übergeben werden muss. Diese Methode ist auch nicht auf Indexbezeichnungen anwendbar. Zum Beispiel, wenn Sie dies bestanden haben:

    df.columns = ['a','b','c','d']

    Dies wird einen Fehler auslösen. Längenfehlanpassung: Die erwartete Achse hat 5 Elemente, neue Werte haben 4 Elemente.

  2. Eine andere Methode ist die Pandas- rename()Methode, mit der ein Index, eine Spalte oder eine Zeile umbenannt wird

    df = df.rename(columns={'$a':'a'})

    Geben Sie hier die Bildbeschreibung ein

Ebenso können Sie beliebige Zeilen oder Spalten ändern.

vibhu_singh
quelle
17
df = pd.DataFrame({'$a': [1], '$b': [1], '$c': [1], '$d': [1], '$e': [1]})

Wenn Ihre neue Spaltenliste in derselben Reihenfolge wie die vorhandenen Spalten vorliegt, ist die Zuordnung einfach:

new_cols = ['a', 'b', 'c', 'd', 'e']
df.columns = new_cols
>>> df
   a  b  c  d  e
0  1  1  1  1  1

Wenn Sie ein Wörterbuch haben, das alte Spaltennamen mit neuen Spaltennamen verknüpft, können Sie Folgendes tun:

d = {'$a': 'a', '$b': 'b', '$c': 'c', '$d': 'd', '$e': 'e'}
df.columns = df.columns.map(lambda col: d[col])  # Or `.map(d.get)` as pointed out by @PiRSquared.
>>> df
   a  b  c  d  e
0  1  1  1  1  1

Wenn Sie keine Listen- oder Wörterbuchzuordnung haben, können Sie das führende $Symbol über ein Listenverständnis entfernen:

df.columns = [col[1:] if col[0] == '$' else col for col in df]
Alexander
quelle
2
Anstelle von lambda col: d[col]Ihnen könnte passieren d.get... so würde es aussehendf.columns.map(d.get)
piRSquared
15

Lassen Sie uns das Umbenennen anhand eines kleinen Beispiels verstehen ...

1. Spalten mit Mapping umbenennen:

df = pd.DataFrame({"A": [1, 2, 3], "B": [4, 5, 6]}) #creating a df with column name A and B
df.rename({"A": "new_a", "B": "new_b"},axis='columns',inplace =True) #renaming column A with 'new_a' and B with 'new_b'

output:
   new_a  new_b
0  1       4
1  2       5
2  3       6

2. Index / Zeilenname mit Zuordnung umbenennen:

df.rename({0: "x", 1: "y", 2: "z"},axis='index',inplace =True) #Row name are getting replaced by 'x','y','z'.

output:
       new_a  new_b
    x  1       4
    y  2       5
    z  3       6
Amar Kumar
quelle
Die am höchsten bewertete Antwort enthält bereits solche Beispiele ...
Itamar Mushkin
14

Eine andere Möglichkeit, die ursprünglichen Spaltenbeschriftungen zu ersetzen, besteht darin, die unerwünschten Zeichen (hier '$') von den ursprünglichen Spaltenbeschriftungen zu entfernen.

Dies könnte durch Ausführen einer for-Schleife über df.columns und Anhängen der entfernten Spalten an df.columns geschehen sein.

Stattdessen können wir dies ordentlich in einer einzigen Anweisung tun, indem wir das Listenverständnis wie folgt verwenden:

df.columns = [col.strip('$') for col in df.columns]

(Die stripMethode in Python entfernt das angegebene Zeichen vom Anfang und Ende der Zeichenfolge.)

Kait
quelle
2
Können Sie erklären, wie / warum das funktioniert? Das wird die Antwort für zukünftige Leser wertvoller machen.
Dan Lowe
12

Ganz einfach nur benutzen

df.columns = ['Name1', 'Name2', 'Name3'...]

und es wird die Spaltennamen in der Reihenfolge zuweisen, in der Sie sie setzen

Thodoris P.
quelle
10

Sie könnten dafür verwenden str.slice:

df.columns = df.columns.str.slice(1)
Anton Protopopov
quelle
1
PS: Dies ist ein ausführlicheres Äquivalent zu df.columns.str[1:]... wahrscheinlich besser zu verwenden, es ist kürzer und offensichtlicher.
cs95
9

Ich weiß, dass diese Frage und Antwort zu Tode gekaut wurde. Aber ich bezog mich darauf, um mich für eines der Probleme zu inspirieren, die ich hatte. Ich war in der Lage, es mit Teilen aus verschiedenen Antworten zu lösen und so meine Antwort zu geben, falls jemand es braucht.

Meine Methode ist generisch, wobei Sie zusätzliche Trennzeichen durch Kommatrennung hinzufügen können delimiters= Variable und zukunftssicher machen.

Arbeitscode:

import pandas as pd
import re


df = pd.DataFrame({'$a':[1,2], '$b': [3,4],'$c':[5,6], '$d': [7,8], '$e': [9,10]})

delimiters = '$'
matchPattern = '|'.join(map(re.escape, delimiters))
df.columns = [re.split(matchPattern, i)[1] for i in df.columns ]

Ausgabe:

>>> df
   $a  $b  $c  $d  $e
0   1   3   5   7   9
1   2   4   6   8  10

>>> df
   a  b  c  d   e
0  1  3  5  7   9
1  2  4  6  8  10
Anil_M
quelle
8

Beachten Sie, dass dieser Ansatz für einen MultiIndex nicht funktioniert. Für einen MultiIndex müssen Sie Folgendes tun:

>>> df = pd.DataFrame({('$a','$x'):[1,2], ('$b','$y'): [3,4], ('e','f'):[5,6]})
>>> df
   $a $b  e
   $x $y  f
0  1  3  5
1  2  4  6
>>> rename = {('$a','$x'):('a','x'), ('$b','$y'):('b','y')}
>>> df.columns = pandas.MultiIndex.from_tuples([
        rename.get(item, item) for item in df.columns.tolist()])
>>> df
   a  b  e
   x  y  f
0  1  3  5
1  2  4  6
Ochse
quelle
8

Eine andere Möglichkeit besteht darin, mit einem regulären Ausdruck umzubenennen:

import pandas as pd
import re

df = pd.DataFrame({'$a':[1,2], '$b':[3,4], '$c':[5,6]})

df = df.rename(columns=lambda x: re.sub('\$','',x))
>>> df
   a  b  c
0  1  3  5
1  2  4  6
sbha
quelle
6

Wenn Sie mit einer Vielzahl von Spalten umgehen müssen, die vom bereitstellenden System außerhalb Ihrer Kontrolle benannt wurden, habe ich den folgenden Ansatz entwickelt, der eine Kombination aus einem allgemeinen Ansatz und spezifischen Ersetzungen auf einmal darstellt.

Erstellen Sie zunächst ein Wörterbuch aus den Spaltennamen der Datenrahmen mithilfe von Regex-Ausdrücken, um bestimmte Anhänge mit Spaltennamen zu entfernen, und fügen Sie dann dem Wörterbuch bestimmte Ersetzungen hinzu, um die Kernspalten wie später in der empfangenden Datenbank zu benennen.

Dies wird dann auf einmal auf den Datenrahmen angewendet.

dict=dict(zip(df.columns,df.columns.str.replace('(:S$|:C1$|:L$|:D$|\.Serial:L$)','')))
dict['brand_timeseries:C1']='BTS'
dict['respid:L']='RespID'
dict['country:C1']='CountryID'
dict['pim1:D']='pim_actual'
df.rename(columns=dict, inplace=True)
matthhias
quelle
5

Zusätzlich zu der bereits bereitgestellten Lösung können Sie alle Spalten ersetzen, während Sie die Datei lesen. Wir können namesund verwendenheader=0 tun.

Zuerst erstellen wir eine Liste der Namen, die wir als Spaltennamen verwenden möchten:

import pandas as pd

ufo_cols = ['city', 'color reported', 'shape reported', 'state', 'time']
ufo.columns = ufo_cols

ufo = pd.read_csv('link to the file you are using', names = ufo_cols, header = 0)

In diesem Fall werden alle Spaltennamen durch die Namen ersetzt, die Sie in Ihrer Liste haben.

Stryker
quelle
4

Hier ist eine nette kleine Funktion, mit der ich gerne tippe:

def rename(data, oldnames, newname): 
    if type(oldnames) == str: #input can be a string or list of strings 
        oldnames = [oldnames] #when renaming multiple columns 
        newname = [newname] #make sure you pass the corresponding list of new names
    i = 0 
    for name in oldnames:
        oldvar = [c for c in data.columns if name in c]
        if len(oldvar) == 0: 
            raise ValueError("Sorry, couldn't find that column in the dataset")
        if len(oldvar) > 1: #doesn't have to be an exact match 
            print("Found multiple columns that matched " + str(name) + " :")
            for c in oldvar:
                print(str(oldvar.index(c)) + ": " + str(c))
            ind = input('please enter the index of the column you would like to rename: ')
            oldvar = oldvar[int(ind)]
        if len(oldvar) == 1:
            oldvar = oldvar[0]
        data = data.rename(columns = {oldvar : newname[i]})
        i += 1 
    return data   

Hier ist ein Beispiel, wie es funktioniert:

In [2]: df = pd.DataFrame(np.random.randint(0,10,size=(10, 4)), columns=['col1','col2','omg','idk'])
#first list = existing variables
#second list = new names for those variables
In [3]: df = rename(df, ['col','omg'],['first','ohmy']) 
Found multiple columns that matched col :
0: col1
1: col2

please enter the index of the column you would like to rename: 0

In [4]: df.columns
Out[5]: Index(['first', 'col2', 'ohmy', 'idk'], dtype='object')
seeiespi
quelle
1
Der Anwendungsfall für eine solche Funktion ist äußerst selten. In den meisten Fällen weiß ich, wonach ich suche und in was ich es umbenennen möchte. Ich würde es einfach selbst zuweisen / ändern.
cs95
1
@ cs95 Ich arbeite in der Regel mit großen nationalen oder internationalen Umfragen, bei denen Variablen Variablennamen codiert haben, die je nach Antwortoptionen, Likert-Skalen und Verzweigung mit Präfixen beginnen (z. B. EDU_2913.443, EDU_2913.421, ...). Diese Funktion war sehr nützlich für mich bei der Arbeit mit diesen Arten von Sets, ich verstehe, wenn es nicht für Sie ist :)
seeiespi
4

Das Umbenennen von Spalten in Pandas ist eine einfache Aufgabe.

df.rename(columns = {'$a':'a','$b':'b','$c':'c','$d':'d','$e':'e'},inplace = True)
Nirali Khoda
quelle
2

Angenommen, Sie können reguläre Ausdrücke verwenden. Diese Lösung macht die manuelle Codierung mit Regex überflüssig

import pandas as pd
import re

srch=re.compile(r"\w+")

data=pd.read_csv("CSV_FILE.csv")
cols=data.columns
new_cols=list(map(lambda v:v.group(),(list(map(srch.search,cols)))))
data.columns=new_cols
Kaustubh J.
quelle
2
Bei Stack Overflow empfiehlt es sich, eine Erklärung hinzuzufügen, warum Ihre Lösung funktionieren sollte oder besser ist als die vorhandenen Lösungen. Weitere Informationen finden Sie unter Beantworten .
Samuel Liew
Beachten Sie, dass die am besten bewertete Antwort eine Form der harten Codierung erfordert und die am schlechtesten bewertete Antwort nur einen beschreibenden und prozeduralen Ansatz erfordert.
Kaustubh J
Es gibt bessere (besser lesbare) Lösungen, die auch Regex verwenden. Dies ist weitaus mehr als für einen einfachen Umbenennungsvorgang erforderlich. Es besteht auch die Gefahr, dass das Muster mit nichts übereinstimmt. In diesem Fall haben Sie nichts unternommen, um Fehler zu behandeln.
cs95