Bagaimana cara mengurutkan dataFrame dalam python panda dengan dua atau lebih kolom?

Jawaban:

454

Pada rilis 0.17.0, sortmetode ini tidak digunakan lagi sort_values. sorttelah sepenuhnya dihapus dalam rilis 0.20.0. Argumen (dan hasil) tetap sama:

df.sort_values(['a', 'b'], ascending=[True, False])

Anda dapat menggunakan argumen naik sort:

df.sort(['a', 'b'], ascending=[True, False])

Sebagai contoh:

In [11]: df1 = pd.DataFrame(np.random.randint(1, 5, (10,2)), columns=['a','b'])

In [12]: df1.sort(['a', 'b'], ascending=[True, False])
Out[12]:
   a  b
2  1  4
7  1  3
1  1  2
3  1  2
4  3  2
6  4  4
0  4  3
9  4  3
5  4  1
8  4  1

Seperti yang dikomentari oleh @renadeen

Sortir tidak ada di tempatnya secara default! Jadi, Anda harus menetapkan hasil metode sortir ke variabel atau menambahkan inplace = Benar ke pemanggilan metode.

yaitu, jika Anda ingin menggunakan kembali df1 sebagai DataFrame yang diurutkan:

df1 = df1.sort(['a', 'b'], ascending=[True, False])

atau

df1.sort(['a', 'b'], ascending=[True, False], inplace=True)
Andy Hayden
sumber
6
Sortir tidak ada di tempatnya secara default! Jadi, Anda harus menetapkan hasil sortmetode ke variabel atau menambah inplace=Truepanggilan metode.
renadeen
2
@renadeen poin yang sangat bagus, saya telah memperbarui dengan jawaban dengan komentar itu.
Andy Hayden
1
Saya terkejut mengetahui hari ini bahwa jenis itu sudah usang! Berdasarkan beberapa pendapat dalam postingan meta ini: meta.stackoverflow.com/questions/297404/... Saya memutuskan untuk menambahkan jawaban baru daripada mencoba mengeditnya
Kyle Heuton
2
@Snoozer Ya, saya kira sort tidak akan pernah pergi (terutama karena ini digunakan secara luas dalam buku Wes), tetapi ada beberapa perubahan besar dalam memanggil sort . Terima kasih! .. Saya benar-benar perlu mengotomatiskan melalui semua 1000 jawaban panda saya untuk penghentian!
Andy Hayden
40

Pada panda 0.17.0, DataFrame.sort()sudah usang, dan diatur untuk dihapus dalam versi panda di masa depan. Cara untuk mengurutkan dataframe berdasarkan nilainya sekarang adalahDataFrame.sort_values

Dengan demikian, jawaban atas pertanyaan Anda sekarang adalah

df.sort_values(['b', 'c'], ascending=[True, False], inplace=True)
Kyle Heuton
sumber
4

Untuk kerangka data data numerik yang besar, Anda dapat melihat peningkatan kinerja yang signifikan melalui numpy.lexsort, yang melakukan pengurutan tidak langsung menggunakan urutan kunci:

import pandas as pd
import numpy as np

np.random.seed(0)

df1 = pd.DataFrame(np.random.randint(1, 5, (10,2)), columns=['a','b'])
df1 = pd.concat([df1]*100000)

def pdsort(df1):
    return df1.sort_values(['a', 'b'], ascending=[True, False])

def lex(df1):
    arr = df1.values
    return pd.DataFrame(arr[np.lexsort((-arr[:, 1], arr[:, 0]))])

assert (pdsort(df1).values == lex(df1).values).all()

%timeit pdsort(df1)  # 193 ms per loop
%timeit lex(df1)     # 143 ms per loop

Satu kekhasan adalah bahwa urutan pengurutan yang ditentukan dengan numpy.lexsortdibalik: (-'b', 'a')mengurutkan berdasarkan seri aterlebih dahulu. Kami meniadakan seri buntuk mencerminkan bahwa kami ingin seri ini dalam urutan menurun.

Perlu diketahui bahwa np.lexsorthanya mengurutkan dengan nilai numerik, sementara pd.DataFrame.sort_valuesberfungsi dengan string atau nilai numerik. Menggunakan np.lexsortdengan string akan memberikan: TypeError: bad operand type for unary -: 'str'.

jpp
sumber