Pandas: группировка и упорядочивание групп на основе максимального значения в каждой группе

#python #pandas

#python #pandas

Вопрос:

У меня есть фрейм данных Pandas, который содержит треки, оценку и некоторые другие столбцы.

Я хочу сгруппировать по «дорожкам», а затем отсортировать эти группы на основе максимального значения в «счете».

Пример фрейма данных:

 tracks       score
20            2.2
20            1.5
25            3.5
24            1.2
24            5.5
  

Ожидаемый результат (я хочу сравнить самые высокие значения из каждой группы и отсортировать всю группу от самого высокого к самому низкому, хотя я не хочу потерять какие-либо другие данные — значит, я хочу показать все строки):

 tracks       score
24            5.5
              1.2
25            3.5
20            2.2
              1.5
  

В настоящее время я получаю следующий вывод (моя оценка отсортирована, но после group by мои треки отсортированы на основе номеров треков):

     tracks       score
20            2.2
              1.5
24            5.5
              4.2
25            3.5
  

Мой подход до сих пор:
1. Я отсортировал все значения по количеству баллов

 sub_df = sub_df.sort_values("score")
  
  1. Затем я делаю следующее, чтобы получить выходные данные (мне нужно в формате словаря):

url_dict = sub_df.groupby('track')['url'].apply(list).to_dict()

Я также пытался использовать OrderedDict, но это бесполезно (по крайней мере, на данный момент), поскольку команда groupBy отправляет неправильную последовательность данных.

Pandas = 0.23, Python = 3.6.4

Ответ №1:

Создайте вспомогательный столбец по GroupBy.transform и отсортируйте по нескольким столбцам по DataFrame.sort_values , последний столбец удаляет вспомогательный:

 sub_df['max'] = sub_df.groupby('tracks')['score'].transform('max')

sub_df = sub_df.sort_values(["max","score"], ascending=False).drop('max', axis=1)
#if necessary sorting also by tracks column
#sub_df = sub_df.sort_values(["max","tracks","score"], ascending=False).drop('max', axis=1)
print (sub_df)
   tracks  score
4      24    5.5
3      24    1.2
2      25    3.5
0      20    2.2
1      20    1.5
  

Комментарии:

1. ты бог pandas. вы ответили на большее количество моих вопросов pandas, чем я могу сосчитать!

Ответ №2:

может быть немного длинновато, но это то, что я использую:

сначала задайте индекс:

 df.set_index(['x', 'y'], inplace=True)
  

затем используйте groupby в дважды отсортированном фрейме данных на основе индекса

 new_df = df.groupby(level=[0,1]).sum().reset_index() 
          .sort_values(['x', 'y'], ascending=[1,0]).groupby('x').head(1)
  

при этом будет показано только максимальное значение, если вы хотите увидеть все, удалите «head (1)».