Supposons que j'ai un cadre de données avec des colonnes a
, b
et c
, je veux trier le cadre de données par colonne b
dans l'ordre croissant, et par colonne c
par ordre décroissant, comment faire cela?
À partir de la version 0.17.0, la méthode sort
était obsolète en faveur de sort_values
. sort
a été complètement supprimé de la version 0.20.0. Les arguments (et les résultats) restent les mêmes:
_df.sort_values(['a', 'b'], ascending=[True, False])
_
Vous pouvez utiliser l'argument croissant de sort
:
_df.sort(['a', 'b'], ascending=[True, False])
_
Par exemple:
_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
_
Commenté par @renadeen
Le tri n'est pas en place par défaut! Vous devez donc affecter le résultat de la méthode de tri à une variable ou ajouter inplace = True à un appel de méthode.
autrement dit, si vous souhaitez réutiliser df1 en tant que DataFrame trié:
_df1 = df1.sort(['a', 'b'], ascending=[True, False])
_
ou
_df1.sort(['a', 'b'], ascending=[True, False], inplace=True)
_
À partir de pandas 0.17.0, DataFrame.sort()
est obsolète et doit être supprimé dans une version ultérieure de pandas. Le moyen de trier un cadre de données en fonction de ses valeurs est désormais DataFrame.sort_values
En tant que tel, la réponse à votre question serait maintenant
df.sort_values(['b', 'c'], ascending=[True, False], inplace=True)
Pour les grandes trames de données numériques, vous pouvez constater une amélioration significative des performances via numpy.lexsort
, qui effectue un tri indirect à l'aide d'une séquence de clés:
_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
_
Une particularité est que l'ordre de tri défini avec _numpy.lexsort
_ est inversé: _(-'b', 'a')
_ trie par série a
en premier. Nous nions la série b
pour refléter le fait que nous voulons cette série par ordre décroissant.