web-dev-qa-db-fra.com

Trier les séries de données d'un pandas par nom de mois?

J'ai un objet Series qui a:

    date   price
    dec      12
    may      15
    apr      13
    ..

Problème posé: Je souhaite le faire apparaître par mois, calculer le prix moyen pour chaque mois et le présenter de manière triée par mois.

Sortie désirée:

 month mean_price
  Jan    XXX
  Feb    XXX
  Mar    XXX

J'ai pensé faire une liste et la transmettre à une fonction de tri:

months = ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"]

mais sort_values ​​ ne supporte pas cela pour les séries.

Un gros problème que j'ai est que même si

df = df.sort_values(by='date',ascending=True,inplace=True) fonctionneà la df initiale, mais après que j’ai fait une groupby, elle n’a pas maintenu l’ordre sortant de la df triée.

Pour conclure, j'avais besoin de la trame de données initiale de ces deux colonnes. Trié la colonne datetime et via un groupe en utilisant le mois (dt.strftime ('% B')), le tri s’est égaré. Maintenant, je dois trier par nom de mois.


Mon code:

df # has 5 columns though I need the column 'date' and 'price'

df.sort_values(by='date',inplace=True) #at this part it is sorted according to date, great
total=(df.groupby(df['date'].dt.strftime('%B'))['price'].mean()) # Though now it is not as it was but instead the months appear alphabetically
5
J_p

Merci @Brad Solomon pour avoir offert un moyen plus rapide de capitaliser les chaînes! 

Note 1 La réponse de Brad Solomon utilisant pd.categorical devrait économiser davantage vos ressources que ma réponse. Il a montré comment assigner un ordre à vos données catégoriques. Vous ne devriez pas le manquer: P

Alternativement, vous pouvez utiliser.

df = pd.DataFrame([["dec", 12], ["jan", 40], ["mar", 11], ["aug", 21],
                  ["aug", 11], ["jan", 11], ["jan", 1]], 
                   columns=["Month", "Price"])
# Preprocessing: capitalize `jan`, `dec` to `Jan` and `Dec`
df["Month"] = df["Month"].str.capitalize()

# Now the dataset should look like
#   Month Price
#   -----------
#    Dec    XX
#    Jan    XX
#    Apr    XX

# make it a datetime so that we can sort it: 
# use %b because the data use the abbriviation of month
df["Month"] = pd.to_datetime(df.Month, format='%b', errors='coerce').dt.month
df = df.sort_values(by="Month")

total = (df.groupby(df['Month"])['Price'].mean())

# total 
Month
1     17.333333
3     11.000000
8     16.000000
12    12.000000

Note 2groupby par défaut triera les clés de groupe pour vous. Sachez que vous devez utiliser la même clé pour trier et grouper dans les fonctions df = df.sort_values(by=SAME_KEY) et total = (df.groupby(df[SAME_KEY])['Price'].mean()).. Sinon, vous risquez d’obtenir un comportement inattendu. Voir Groupby préserver l'ordre parmi les groupes? De quelle manière? Pour plus d'informations.

Note 3 Une méthode plus efficace en calcul consiste à calculer la moyenne puis à effectuer le tri par mois. De cette manière, il vous suffit de trier sur 12 éléments plutôt que sur la totalité de la variable df. Cela réduira les coûts de calcul si vous n'avez pas besoin de df pour être trié.

Note 4 Pour les personnes ayant déjà month comme index, et vous demandez comment le rendre catégorique, jetez un coup d'œil à pandas .CategoricalIndex jezrael a un exemple concret sur la commande par index in Les séries de pandas sont triées par mois

2
Tai

Vous pouvez utiliser des données catégoriques pour permettre un tri correct:

months = ["Jan", "Feb", "Mar", "Apr", "May", "Jun", 
          "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"]
df['months'] = pd.Categorical(df['months'], categories=months, ordered=True)
df.sort_values(...)  # same as you have now; can use inplace=True

Lorsque vous spécifiez les catégories, les pandas mémorisent l'ordre de spécification comme ordre de tri par défaut.

Docs: Catégories de pandas> tri et ordre .

6
Brad Solomon

utilisez Sort_Dataframeby_Month function pour trier les noms de mois par ordre chronologique

Les paquets doivent être installés.

$ pip install sorted-months-weekdays
$ pip install sort-dataframeby-monthorweek

exemple:

from sorted_months_weekdays import *

from sort_dataframeby_monthorweek import *

df = pd.DataFrame([['Jan',23],['Jan',16],['Dec',35],['Apr',79],['Mar',53],['Mar',12],['Feb',3]], columns=['Month','Sum'])
df
Out[11]: 
  Month  Sum
0   Jan   23
1   Jan   16
2   Dec   35
3   Apr   79
4   Mar   53
5   Mar   12
6   Feb    3

Pour trier dataframe par mois, utilisez la fonction ci-dessous

Sort_Dataframeby_Month(df=df,monthcolumnname='Month')
Out[14]: 
  Month  Sum
0   Jan   23
1   Jan   16
2   Feb    3
3   Mar   53
4   Mar   12
5   Apr   79
6   Dec   35
0
Dinesh Babu

Vous pouvez ajouter la valeur numérique du mois avec le nom dans l'index ("01 janvier"), faire un tri puis supprimer le nombre

total=(df.groupby(df['date'].dt.strftime('%m %B'))['price'].mean()).sort_index()

Cela peut ressembler à ça:

01 January  xxx
02 February     yyy
03 March    zzz
04 April    ttt

 total.index = [ x.split()[1] for x in total.index ]

January xxx
February yyy
March zzz
April ttt
0
Zellint