Wie ändere ich die Reihenfolge der DataFrame-Spalten?

879

Ich habe folgendes DataFrame( df):

import numpy as np
import pandas as pd

df = pd.DataFrame(np.random.rand(10, 5))

Ich füge weitere Spalten durch Zuweisung hinzu:

df['mean'] = df.mean(1)

Wie kann ich die Spalte meannach vorne verschieben, dh als erste Spalte festlegen, wobei die Reihenfolge der anderen Spalten unberührt bleibt?

Timmie
quelle
1
Eine verallgemeinerte NumPy-basierte Lösung finden Sie unter Verschieben einer Spalte in einem Pandas-Datenrahmen. Dabei wird nur eine Spaltenebene angenommen, dh nein MultiIndex.
jpp

Antworten:

853

Eine einfache Möglichkeit wäre, den Datenrahmen mit einer Liste der Spalten neu zuzuweisen, die nach Bedarf neu angeordnet werden.

Das haben Sie jetzt:

In [6]: df
Out[6]:
          0         1         2         3         4      mean
0  0.445598  0.173835  0.343415  0.682252  0.582616  0.445543
1  0.881592  0.696942  0.702232  0.696724  0.373551  0.670208
2  0.662527  0.955193  0.131016  0.609548  0.804694  0.632596
3  0.260919  0.783467  0.593433  0.033426  0.512019  0.436653
4  0.131842  0.799367  0.182828  0.683330  0.019485  0.363371
5  0.498784  0.873495  0.383811  0.699289  0.480447  0.587165
6  0.388771  0.395757  0.745237  0.628406  0.784473  0.588529
7  0.147986  0.459451  0.310961  0.706435  0.100914  0.345149
8  0.394947  0.863494  0.585030  0.565944  0.356561  0.553195
9  0.689260  0.865243  0.136481  0.386582  0.730399  0.561593

In [7]: cols = df.columns.tolist()

In [8]: cols
Out[8]: [0L, 1L, 2L, 3L, 4L, 'mean']

Ordnen colsSie es nach Belieben neu an. So habe ich das letzte Element an die erste Position verschoben:

In [12]: cols = cols[-1:] + cols[:-1]

In [13]: cols
Out[13]: ['mean', 0L, 1L, 2L, 3L, 4L]

Ordnen Sie dann den Datenrahmen folgendermaßen neu an:

In [16]: df = df[cols]  #    OR    df = df.ix[:, cols]

In [17]: df
Out[17]:
       mean         0         1         2         3         4
0  0.445543  0.445598  0.173835  0.343415  0.682252  0.582616
1  0.670208  0.881592  0.696942  0.702232  0.696724  0.373551
2  0.632596  0.662527  0.955193  0.131016  0.609548  0.804694
3  0.436653  0.260919  0.783467  0.593433  0.033426  0.512019
4  0.363371  0.131842  0.799367  0.182828  0.683330  0.019485
5  0.587165  0.498784  0.873495  0.383811  0.699289  0.480447
6  0.588529  0.388771  0.395757  0.745237  0.628406  0.784473
7  0.345149  0.147986  0.459451  0.310961  0.706435  0.100914
8  0.553195  0.394947  0.863494  0.585030  0.565944  0.356561
9  0.561593  0.689260  0.865243  0.136481  0.386582  0.730399
Ein Mann
quelle
17
Wenn Sie erhalten, dass "str" ​​- und "list" -Objekte nicht verkettet werden können, stellen Sie sicher, dass Sie [] den str-Wert in cols: cols = [cols [7]] + cols [: 7] + cols [8:]
moeabdol
3
@FooBar Das ist keine festgelegte Vereinigung, sondern eine Verkettung von zwei geordneten Listen.
Aman
3
@Aman Ich weise nur darauf hin, dass Ihr Code veraltet ist. Die Bearbeitung Ihrer Post liegt in Ihrem Ermessen.
FooBar
2
@FooBar, der Typ von colsist list; Es sind sogar Duplikate zulässig (die bei Verwendung im Datenrahmen verworfen werden). Sie denken an IndexObjekte.
Alexis
8
Dies impliziert das Kopieren ALLER Daten, was sehr ineffizient ist. Ich wünschte, Pandas hätten eine Möglichkeit, dies zu tun, ohne eine Kopie zu erstellen.
Konstantin
442

Sie könnten auch so etwas tun:

df = df[['mean', '0', '1', '2', '3']]

Sie können die Liste der Spalten erhalten mit:

cols = list(df.columns.values)

Die Ausgabe erzeugt:

['0', '1', '2', '3', 'mean']

... die dann einfach manuell neu anzuordnen ist, bevor sie in die erste Funktion übernommen wird

freddygv
quelle
8
Sie könnten auch die Liste der Spalten mit Liste (df.columns)
Jim
8
oderdf.columns.tolist()
Jim
Ordnen Sie für Neulinge wie mich die Liste neu, die Sie von cols erhalten. Dann ist df = df [cols], dh die neu angeordnete Liste wird ohne nur einen Satz von Klammern in den ersten Ausdruck eingefügt.
Sid
df = df[['mean1', 0, 1, 2, 3]]Spaltennamen sind ganze Zahlen in 3.x ✓
Prosti
1
Ich denke nicht, dass dies eine gute Antwort ist, da es keinen Code zum Ändern der Spaltenreihenfolge eines Datenrahmens enthält. Angenommen, ich importiere eine CSV-Datei als Pandas PDF als pd.read_csv(). Wie kann Ihre Antwort verwendet werden, um die Spaltenreihenfolge zu ändern?
Robvh
312

Weisen Sie einfach die Spaltennamen in der gewünschten Reihenfolge zu:

In [39]: df
Out[39]: 
          0         1         2         3         4  mean
0  0.172742  0.915661  0.043387  0.712833  0.190717     1
1  0.128186  0.424771  0.590779  0.771080  0.617472     1
2  0.125709  0.085894  0.989798  0.829491  0.155563     1
3  0.742578  0.104061  0.299708  0.616751  0.951802     1
4  0.721118  0.528156  0.421360  0.105886  0.322311     1
5  0.900878  0.082047  0.224656  0.195162  0.736652     1
6  0.897832  0.558108  0.318016  0.586563  0.507564     1
7  0.027178  0.375183  0.930248  0.921786  0.337060     1
8  0.763028  0.182905  0.931756  0.110675  0.423398     1
9  0.848996  0.310562  0.140873  0.304561  0.417808     1

In [40]: df = df[['mean', 4,3,2,1]]

Jetzt erscheint vorne die Spalte "Mittelwert":

In [41]: df
Out[41]: 
   mean         4         3         2         1
0     1  0.190717  0.712833  0.043387  0.915661
1     1  0.617472  0.771080  0.590779  0.424771
2     1  0.155563  0.829491  0.989798  0.085894
3     1  0.951802  0.616751  0.299708  0.104061
4     1  0.322311  0.105886  0.421360  0.528156
5     1  0.736652  0.195162  0.224656  0.082047
6     1  0.507564  0.586563  0.318016  0.558108
7     1  0.337060  0.921786  0.930248  0.375183
8     1  0.423398  0.110675  0.931756  0.182905
9     1  0.417808  0.304561  0.140873  0.310562
fixxxer
quelle
7
Macht es eine Kopie?
user3226167
21
@NicholasMorley - Dies ist nicht die beste Antwort, wenn Sie beispielsweise 1000 Spalten in Ihrem df haben.
AGS
1
Es scheint nicht so, als würden Sie zuweisen, <df>.columnswie Sie es ursprünglich behaupten
Björks größter Fan
8
Dies ist die beste Antwort für eine kleine Anzahl von Spalten.
Dongkyu Choi
2
Dies ist nur eine Kopie der früheren Antwort von @freddygv. Das sollte die akzeptierte Antwort sein, nicht diese.
James Hirschorn
134

Wie wäre es mit:

df.insert(0, 'mean', df.mean(1))

http://pandas.pydata.org/pandas-docs/stable/dsintro.html#column-selection-addition-deletion

Wes McKinney
quelle
35
Könnte dies eine zukünftige Funktion sein pandas? so etwas wie df.move(0,df.mean)?
Jason
Oh man, es funktioniert sogar so df_metadata.insert(0,'Db_name',"raw_data")(Code nicht relevant für diesen Thread)
Aetos
3
Wunderschönen. Und es passiert auch an Ort und Stelle.
Cucu8
2
Dies ist eine skalierbare Lösung, da andere Lösungen Spaltennamen manuell eingeben.
CKM
Dies funktioniert für die Frage des OP beim Erstellen einer neuen Spalte, nicht jedoch für das Verschieben einer Spalte. Versuch, Ergebnisse zu verschieben*** ValueError: cannot insert mean, already exists
Spinup
122

In Ihrem Fall,

df = df.reindex(columns=['mean',0,1,2,3,4])

wird genau das tun, was Sie wollen.

In meinem Fall (allgemeine Form):

df = df.reindex(columns=sorted(df.columns))
df = df.reindex(columns=(['opened'] + list([a for a in df.columns if a != 'opened']) ))
Alvaro Joao
quelle
2
Ich habe versucht zu setzen, copy=Falseaber es sieht so aus, als würde reindex_axisimmer noch eine Kopie erstellt.
Konstantin
1
@Konstantin können Sie eine weitere Frage zu diesem Problem erstellen? Es wäre besser, mehr Kontext zu haben
Alvaro Joao
57

Sie müssen eine neue Liste Ihrer Spalten in der gewünschten Reihenfolge erstellen und dann df = df[cols]die Spalten in dieser neuen Reihenfolge neu anordnen.

cols = ['mean']  + [col for col in df if col != 'mean']
df = df[cols]

Sie können auch einen allgemeineren Ansatz verwenden. In diesem Beispiel wird die letzte Spalte (angezeigt durch -1) als erste Spalte eingefügt.

cols = [df.columns[-1]] + [col for col in df if col != df.columns[-1]]
df = df[cols]

Sie können diesen Ansatz auch verwenden, um Spalten in einer gewünschten Reihenfolge neu anzuordnen, wenn sie im DataFrame vorhanden sind.

inserted_cols = ['a', 'b', 'c']
cols = ([col for col in inserted_cols if col in df] 
        + [col for col in df if col not in inserted_cols])
df = df[cols]
Alexander
quelle
45
import numpy as np
import pandas as pd
df = pd.DataFrame()
column_names = ['x','y','z','mean']
for col in column_names: 
    df[col] = np.random.randint(0,100, size=10000)

Sie können folgende Lösungen ausprobieren:

Lösung 1:

df = df[ ['mean'] + [ col for col in df.columns if col != 'mean' ] ]

Lösung 2:


df = df[['mean', 'x', 'y', 'z']]

Lösung 3:

col = df.pop("mean")
df = df.insert(0, col.name, col)

Lösung 4:

df.set_index(df.columns[-1], inplace=True)
df.reset_index(inplace=True)

Lösung 5:

cols = list(df)
cols = [cols[-1]] + cols[:-1]
df = df[cols]

Lösung 6:

order = [1,2,3,0] # setting column's order
df = df[[df.columns[i] for i in order]]

Zeitvergleich:

Lösung 1:

CPU-Zeiten: Benutzer 1,05 ms, System: 35 µs, Gesamt: 1,08 ms Wandzeit: 995 µs

Lösung 2 :

CPU-Zeiten: Benutzer 933 µs, System: 0 ns, Gesamt: 933 µs Wandzeit: 800 µs

Lösung 3 :

CPU-Zeiten: Benutzer 0 ns, System: 1,35 ms, Gesamt: 1,35 ms Wandzeit: 1,08 ms

Lösung 4 :

CPU-Zeiten: Benutzer 1,23 ms, System: 45 µs, Gesamt: 1,27 ms Wandzeit: 986 µs

Lösung 5 :

CPU-Zeiten: Benutzer 1,09 ms, System: 19 µs, Gesamt: 1,11 ms Wandzeit: 949 µs

Lösung 6 :

CPU-Zeiten: Benutzer 955 µs, System: 34 µs, Gesamt: 989 µs Wandzeit: 859 µs

Pygirl
quelle
1
So eine schöne Antwort, danke.
Qasimalbaqali
1
Lösung 1 ist das, was ich brauchte, da ich zu viele Spalten (53) habe, danke
ratnesh
@ Pygirl Welcher Wert zeigt die tatsächlich verbrauchte Zeit an? (Benutzer, System, Gesamt- oder Wandzeit)
sergzemsk
1
Dies ist für mich die beste Antwort auf das Problem. So viele Lösungen (einschließlich einer, die ich brauchte) und einfacher Ansatz. Vielen Dank!
Gustavo Rottgering
1
Lösung 6 (kein Listenverständnis):df = df.iloc[:, [1, 2, 3, 0]]
Dmitriy Work
43

Ab August 2018:

Wenn Ihre Spaltennamen zu lang sind, um sie einzugeben, können Sie die neue Reihenfolge über eine Liste von Ganzzahlen mit den folgenden Positionen angeben:

Daten:

          0         1         2         3         4      mean
0  0.397312  0.361846  0.719802  0.575223  0.449205  0.500678
1  0.287256  0.522337  0.992154  0.584221  0.042739  0.485741
2  0.884812  0.464172  0.149296  0.167698  0.793634  0.491923
3  0.656891  0.500179  0.046006  0.862769  0.651065  0.543382
4  0.673702  0.223489  0.438760  0.468954  0.308509  0.422683
5  0.764020  0.093050  0.100932  0.572475  0.416471  0.389390
6  0.259181  0.248186  0.626101  0.556980  0.559413  0.449972
7  0.400591  0.075461  0.096072  0.308755  0.157078  0.207592
8  0.639745  0.368987  0.340573  0.997547  0.011892  0.471749
9  0.050582  0.714160  0.168839  0.899230  0.359690  0.438500

Allgemeines Beispiel:

new_order = [3,2,1,4,5,0]
print(df[df.columns[new_order]])  

          3         2         1         4      mean         0
0  0.575223  0.719802  0.361846  0.449205  0.500678  0.397312
1  0.584221  0.992154  0.522337  0.042739  0.485741  0.287256
2  0.167698  0.149296  0.464172  0.793634  0.491923  0.884812
3  0.862769  0.046006  0.500179  0.651065  0.543382  0.656891
4  0.468954  0.438760  0.223489  0.308509  0.422683  0.673702
5  0.572475  0.100932  0.093050  0.416471  0.389390  0.764020
6  0.556980  0.626101  0.248186  0.559413  0.449972  0.259181
7  0.308755  0.096072  0.075461  0.157078  0.207592  0.400591
8  0.997547  0.340573  0.368987  0.011892  0.471749  0.639745
9  0.899230  0.168839  0.714160  0.359690  0.438500  0.050582

Und für den speziellen Fall der Frage von OP:

new_order = [-1,0,1,2,3,4]
df = df[df.columns[new_order]]
print(df)

       mean         0         1         2         3         4
0  0.500678  0.397312  0.361846  0.719802  0.575223  0.449205
1  0.485741  0.287256  0.522337  0.992154  0.584221  0.042739
2  0.491923  0.884812  0.464172  0.149296  0.167698  0.793634
3  0.543382  0.656891  0.500179  0.046006  0.862769  0.651065
4  0.422683  0.673702  0.223489  0.438760  0.468954  0.308509
5  0.389390  0.764020  0.093050  0.100932  0.572475  0.416471
6  0.449972  0.259181  0.248186  0.626101  0.556980  0.559413
7  0.207592  0.400591  0.075461  0.096072  0.308755  0.157078
8  0.471749  0.639745  0.368987  0.340573  0.997547  0.011892
9  0.438500  0.050582  0.714160  0.168839  0.899230  0.359690

Das Hauptproblem bei diesem Ansatz ist, dass das mehrmalige Aufrufen des gleichen Codes jedes Mal zu unterschiedlichen Ergebnissen führt. Daher muss man vorsichtig sein :)

Yuca
quelle
17

Mit dieser Funktion müssen Sie nicht jede Variable in Ihrem Datensatz auflisten, um nur einige davon zu bestellen.

def order(frame,var):
    if type(var) is str:
        var = [var] #let the command take a string or list
    varlist =[w for w in frame.columns if w not in var]
    frame = frame[var+varlist]
    return frame 

Es werden zwei Argumente benötigt, das erste ist das Dataset, das zweite sind die Spalten im Datensatz, die Sie in den Vordergrund stellen möchten.

In meinem Fall habe ich also einen Datensatz namens Frame mit den Variablen A1, A2, B1, B2, Total und Date. Wenn ich Total nach vorne bringen will, muss ich nur Folgendes tun:

frame = order(frame,['Total'])

Wenn ich Total und Date nach vorne bringen möchte, dann mache ich:

frame = order(frame,['Total','Date'])

BEARBEITEN:

Eine andere nützliche Möglichkeit, dies zu verwenden, besteht darin, dass Sie, wenn Sie eine unbekannte Tabelle haben und nach Variablen mit einem bestimmten Begriff suchen, wie VAR1, VAR2, ... Folgendes ausführen können:

frame = order(frame,[v for v in frame.columns if "VAR" in v])
seeiespi
quelle
17

Ich bin selbst auf eine ähnliche Frage gestoßen und wollte nur hinzufügen, worauf ich mich festgelegt habe. Ich mochte die reindex_axis() methodzum Ändern der Spaltenreihenfolge. Das hat funktioniert:

df = df.reindex_axis(['mean'] + list(df.columns[:-1]), axis=1)

Eine alternative Methode basierend auf dem Kommentar von @Jorge:

df = df.reindex(columns=['mean'] + list(df.columns[:-1]))

Obwohl reindex_axises in Mikro-Benchmarks etwas schneller zu sein scheint als reindex, bevorzuge ich Letzteres wegen seiner Direktheit.

Uhr
quelle
6
Dies war eine gute Lösung, aber reindex_axis wird nicht mehr unterstützt. Ich habe Reindex verwendet und es hat gut funktioniert.
Jorge
15

Einfach machen,

df = df[['mean'] + df.columns[:-1].tolist()]
Napitupulu Jon
quelle
TypeError: 'int' Objekt kann nicht implizit in str konvertiert werden
parvij
könnte API geändert haben, können Sie dies auch tun ... order = df.columns.tolist() df['mean'] = df.mean(1) df.columns = ['mean'] + order
Napitupulu Jon
1
Eine Variation davon hat bei mir gut funktioniert. Mit einer vorhandenen Liste, headersdie zum Erstellen eines Diktats verwendet wurde, das dann zum Erstellen des von mir aufgerufenen DataFrame verwendet wurde df.reindex(columns=headers). Das einzige Problem, auf das ich stieß, war, dass ich bereits aufgerufen df.set_index('some header name', inplace=True)hatte. Als die Neuindizierung abgeschlossen war, wurde eine weitere Spalte hinzugefügt, die benannt wurde, some header nameda die ursprüngliche Spalte jetzt der Index war. Was die oben angegebene Syntax ['mean'] + df.columnsIndex(u'meanAddress', u'meanCity', u'meanFirst Name'...
betrifft,
1
@hlongmore: Ich weiß nicht, dass Ihr vorheriger Code ist, aber die Bearbeitung sollte funktionieren (mit 0.19.2)
Napitupulu Jon
Die Bearbeitung funktioniert tatsächlich (ich bin auf 0.20.2). In meinem Fall habe ich bereits die gewünschten Spalten, daher denke ich, dass df.reindex () das ist, was ich wirklich verwenden sollte.
Hlongmore
11

Sie könnten Folgendes tun (Teile aus Amans Antwort ausleihen):

cols = df.columns.tolist()
cols.insert(0, cols.pop(-1))

cols
>>>['mean', 0L, 1L, 2L, 3L, 4L]

df = df[cols]
otteheng
quelle
10

Geben Sie einfach den Spaltennamen ein, den Sie ändern möchten, und legen Sie den Index für den neuen Speicherort fest.

def change_column_order(df, col_name, index):
    cols = df.columns.tolist()
    cols.remove(col_name)
    cols.insert(index, col_name)
    return df[cols]

Für Ihren Fall wäre dies wie folgt:

df = change_column_order(df, 'mean', 0)
Ccerhan
quelle
Dies wird unterschätzt
zelusp
8

Verschieben einer Spalte an eine beliebige Position:

import pandas as pd
df = pd.DataFrame({"A": [1,2,3], 
                   "B": [2,4,8], 
                   "C": [5,5,5]})

cols = df.columns.tolist()
column_to_move = "C"
new_position = 1

cols.insert(new_position, cols.pop(cols.index(column_to_move)))
df = df[cols]
pomber
quelle
7

Ich denke, das ist eine etwas sauberere Lösung:

df.insert(0,'mean', df.pop("mean"))

Diese Lösung ähnelt der Lösung von @JoeHeffer, ist jedoch ein Liner.

Hier entfernen wir die Spalte "mean"aus dem Datenrahmen und hängen sie an den Index 0mit demselben Spaltennamen an.

erncyp
quelle
5

Hier ist eine Möglichkeit, eine vorhandene Spalte zu verschieben, um den vorhandenen Datenrahmen zu ändern.

my_column = df.pop('column name')
df.insert(3, my_column.name, my_column)
Joe Heffer
quelle
5

Diese Frage wurde beantwortet , bevor aber reindex_axis ist jetzt veraltet , so ich Verwendung vorschlagen würde:

df.reindex(sorted(df.columns), axis=1)
dmvianna
quelle
19
Nein, das ist anders. Dort möchte der Benutzer alle Spalten nach Namen sortieren. Hier möchten sie eine Spalte in die erste Spalte verschieben, während die Reihenfolge der anderen Spalten unberührt bleibt.
smci
1
Was ist, wenn Sie nicht möchten, dass sie sortiert werden?
Chankey Pathak
Dies gibt eine Kopie zurück, funktioniert nicht an Ort und Stelle
Spinup
3

Wie wäre es mit "T"?

df.T.reindex(['mean',0,1,2,3,4]).T
ZEE
quelle
3

@clocker: Ihre Lösung war für mich sehr hilfreich, da ich zwei Spalten aus einem Datenrahmen voranstellen wollte, in dem ich die Namen aller Spalten nicht genau kenne, da sie zuvor aus einer Pivot-Anweisung generiert wurden. Wenn Sie sich also in der gleichen Situation befinden: Um Spalten vorzubringen, deren Namen Sie kennen, und sie dann von "allen anderen Spalten" folgen zu lassen, habe ich die folgende allgemeine Lösung gefunden.

df = df.reindex_axis(['Col1','Col2'] + list(df.columns.drop(['Col1','Col2'])), axis=1)
matthhias
quelle
3

set()::

Ein einfacher Ansatz ist die Verwendung set(), insbesondere wenn Sie eine lange Liste von Spalten haben und diese nicht manuell behandeln möchten:

cols = list(set(df.columns.tolist()) - set(['mean']))
cols.insert(0, 'mean')
df = df[cols]
Shoresh
quelle
2
Eine Warnung: Die Reihenfolge der Spalten
verschwindet,
Interessant! @ user1930402 Ich habe den obigen Ansatz mehrmals ausprobiert und hatte nie ein Problem. Ich werde es noch einmal überprüfen.
Shoresh
2

Ich mochte Shoreshs Antwort , die Set-Funktionalität zum Entfernen von Spalten zu verwenden, wenn Sie den Speicherort nicht kennen. Dies funktionierte jedoch nicht für meinen Zweck, da ich die ursprüngliche Spaltenreihenfolge muss (die beliebige Spaltenbezeichnungen hat).

Ich habe dies jedoch mithilfe von IndexedSet aus dem Boltons-Paket zum Laufen gebracht.

Ich musste auch mehrere Spaltenbeschriftungen erneut hinzufügen, sodass ich für einen allgemeineren Fall den folgenden Code verwendete:

from boltons.setutils import IndexedSet
cols = list(IndexedSet(df.columns.tolist()) - set(['mean', 'std']))
cols[0:0] =['mean', 'std']
df = df[cols]

Ich hoffe, dies ist nützlich für alle, die diesen Thread nach einer allgemeinen Lösung durchsuchen.

Jamelade
quelle
Ich bin ein bisschen überrascht! Ich benutze setes ziemlich oft für diesen Zweck und musste mich nie mit Bestellungen befassen.
Shoresh
2

Sie können verwenden, reindexwelche für beide Achsen verwendet werden kann:

df
#           0         1         2         3         4      mean
# 0  0.943825  0.202490  0.071908  0.452985  0.678397  0.469921
# 1  0.745569  0.103029  0.268984  0.663710  0.037813  0.363821
# 2  0.693016  0.621525  0.031589  0.956703  0.118434  0.484254
# 3  0.284922  0.527293  0.791596  0.243768  0.629102  0.495336
# 4  0.354870  0.113014  0.326395  0.656415  0.172445  0.324628
# 5  0.815584  0.532382  0.195437  0.829670  0.019001  0.478415
# 6  0.944587  0.068690  0.811771  0.006846  0.698785  0.506136
# 7  0.595077  0.437571  0.023520  0.772187  0.862554  0.538182
# 8  0.700771  0.413958  0.097996  0.355228  0.656919  0.444974
# 9  0.263138  0.906283  0.121386  0.624336  0.859904  0.555009

df.reindex(['mean', *range(5)], axis=1)

#        mean         0         1         2         3         4
# 0  0.469921  0.943825  0.202490  0.071908  0.452985  0.678397
# 1  0.363821  0.745569  0.103029  0.268984  0.663710  0.037813
# 2  0.484254  0.693016  0.621525  0.031589  0.956703  0.118434
# 3  0.495336  0.284922  0.527293  0.791596  0.243768  0.629102
# 4  0.324628  0.354870  0.113014  0.326395  0.656415  0.172445
# 5  0.478415  0.815584  0.532382  0.195437  0.829670  0.019001
# 6  0.506136  0.944587  0.068690  0.811771  0.006846  0.698785
# 7  0.538182  0.595077  0.437571  0.023520  0.772187  0.862554
# 8  0.444974  0.700771  0.413958  0.097996  0.355228  0.656919
# 9  0.555009  0.263138  0.906283  0.121386  0.624336  0.859904
Silgon
quelle
2

Hier ist eine Funktion, um dies für eine beliebige Anzahl von Spalten zu tun.

def mean_first(df):
    ncols = df.shape[1]        # Get the number of columns
    index = list(range(ncols)) # Create an index to reorder the columns
    index.insert(0,ncols)      # This puts the last column at the front
    return(df.assign(mean=df.mean(1)).iloc[:,index]) # new df with last column (mean) first
freeB
quelle
2

Hackiest Methode im Buch

df.insert(0,"test",df["mean"])
df=df.drop(columns=["mean"]).rename(columns={"test":"mean"})
Kaustubh J.
quelle
2

Ich denke, diese Funktion ist einfacher. Sie müssen nur eine Teilmenge der Spalten am Anfang oder am Ende oder an beiden angeben:

def reorder_df_columns(df, start=None, end=None):
    """
        This function reorder columns of a DataFrame.
        It takes columns given in the list `start` and move them to the left.
        Its also takes columns in `end` and move them to the right.
    """
    if start is None:
        start = []
    if end is None:
        end = []
    assert isinstance(start, list) and isinstance(end, list)
    cols = list(df.columns)
    for c in start:
        if c not in cols:
            start.remove(c)
    for c in end:
        if c not in cols or c in start:
            end.remove(c)
    for c in start + end:
        cols.remove(c)
    cols = start + cols + end
    return df[cols]
hayj
quelle
1

Ich glaube, @ Amans Antwort ist die beste, wenn Sie den Ort der anderen Spalte kennen.

Wenn Sie den Standort von nicht kennen mean, aber nur seinen Namen haben, können Sie nicht direkt darauf zurückgreifen cols = cols[-1:] + cols[:-1]. Das Folgende ist das nächstbeste, was ich mir vorstellen kann:

meanDf = pd.DataFrame(df.pop('mean'))
# now df doesn't contain "mean" anymore. Order of join will move it to left or right:
meanDf.join(df) # has mean as first column
df.join(meanDf) # has mean as last column
FooBar
quelle
1

Nur umdrehen hilft oft.

df[df.columns[::-1]]

Oder mischen Sie einfach für einen Blick.

import random
cols = list(df.columns)
random.shuffle(cols)
df[cols]
plhn
quelle
0

Die meisten Antworten wurden nicht ausreichend verallgemeinert, und die Methode pandas reindex_axis ist etwas langwierig. Daher biete ich eine einfache Funktion an, um eine beliebige Anzahl von Spalten mithilfe eines Wörterbuchs an eine beliebige Position zu verschieben, wobei key = Spaltenname und value = position zum Verschieben. Wenn Ihr Datenrahmen groß ist, übergeben Sie True 'big_data', und die Funktion gibt die Liste der geordneten Spalten zurück. Mit dieser Liste können Sie Ihre Daten aufteilen.

def order_column(df, columns, big_data = False):

    """Re-Orders dataFrame column(s)
       Parameters : 
       df      -- dataframe
       columns -- a dictionary:
                  key   = current column position/index or column name
                  value = position to move it to  
       big_data -- boolean 
                  True = returns only the ordered columns as a list
                          the user user can then slice the data using this
                          ordered column
                  False = default - return a copy of the dataframe
    """
    ordered_col = df.columns.tolist()

    for key, value in columns.items():

        ordered_col.remove(key)
        ordered_col.insert(value, key)

    if big_data:

        return ordered_col

    return df[ordered_col]

# e.g.
df = pd.DataFrame({'chicken wings': np.random.rand(10, 1).flatten(), 'taco': np.random.rand(10,1).flatten(),
                          'coffee': np.random.rand(10, 1).flatten()})
df['mean'] = df.mean(1)

df = order_column(df, {'mean': 0, 'coffee':1 })

>>>

Ausgabe

col = order_column(df, {'mean': 0, 'coffee':1 }, True)

col
>>>
['mean', 'coffee', 'chicken wings', 'taco']

# you could grab it by doing this

df = df[col]
escha
quelle
0

Ich habe einen sehr speziellen Anwendungsfall für die Neuordnung von Spaltennamen in Pandas. Manchmal erstelle ich eine neue Spalte in einem Datenrahmen, die auf einer vorhandenen Spalte basiert. Standardmäßig fügen Pandas meine neue Spalte am Ende ein, aber ich möchte, dass die neue Spalte neben der vorhandenen Spalte eingefügt wird, von der sie abgeleitet ist.

Geben Sie hier die Bildbeschreibung ein

def rearrange_list(input_list, input_item_to_move, input_item_insert_here):
    '''
    Helper function to re-arrange the order of items in a list.
    Useful for moving column in pandas dataframe.

    Inputs:
        input_list - list
        input_item_to_move - item in list to move
        input_item_insert_here - item in list, insert before 

    returns:
        output_list
    '''
    # make copy for output, make sure it's a list
    output_list = list(input_list)

    # index of item to move
    idx_move = output_list.index(input_item_to_move)

    # pop off the item to move
    itm_move = output_list.pop(idx_move)

    # index of item to insert here
    idx_insert = output_list.index(input_item_insert_here)

    # insert item to move into here
    output_list.insert(idx_insert, itm_move)

    return output_list


import pandas as pd

# step 1: create sample dataframe
df = pd.DataFrame({
    'motorcycle': ['motorcycle1', 'motorcycle2', 'motorcycle3'],
    'initial_odometer': [101, 500, 322],
    'final_odometer': [201, 515, 463],
    'other_col_1': ['blah', 'blah', 'blah'],
    'other_col_2': ['blah', 'blah', 'blah']
})
print('Step 1: create sample dataframe')
display(df)
print()

# step 2: add new column that is difference between final and initial
df['change_odometer'] = df['final_odometer']-df['initial_odometer']
print('Step 2: add new column')
display(df)
print()

# step 3: rearrange columns
ls_cols = df.columns
ls_cols = rearrange_list(ls_cols, 'change_odometer', 'final_odometer')
df=df[ls_cols]
print('Step 3: rearrange columns')
display(df)
pk2019
quelle
0

Eine ziemlich einfache Lösung, die für mich funktioniert hat, ist die Verwendung von .reindex für df.columns:

df=df[df.columns.reindex(['mean',0,1,2,3,4])[0]]
CSQL
quelle