Как ускорить перенос данных из одной таблицы в другую?

У меня есть два фрейма данных df и res. res получен в результате группировки df по столбцу name. Теперь мне нужно в df переписать дынные из столбца idxmaximum, полученного в таблице res, если значение в столбце name таблицы df совпадает со значением index в таблице res

Пример df таблицы:

Name Ноябрь Декабрь Февраль
Алексей 15 10 15
Алексей 10 10 10
Андрей 15 25 15
Алексей 15 15 10
Андрей 25 10 45

Пример res таблицы:

index Ноябрь Декабрь Февраль idxmaximum
Алексей 40 35 35 Ноябрь
Андрей 40 35 60 Февраль

Что хочется получить:

Name Ноябрь Декабрь Февраль num
Алексей 15 10 15 Ноябрь
Алексей 10 10 10 Ноябрь
Андрей 15 25 15 Февраль
Алексей 15 15 10 Ноябрь
Андрей 25 10 45 Февраль

Мой код:

for i in range(df.shape[0]):
    for j in range(res.shape[0]):
        if df.name[i] == res.index[j]:
            df.num[i] = res.idxmaximum[j]

Подскажите, пожалуйста, как можно ускорить данный процесс?


Ответы (2 шт):

Автор решения: MaxU

скорее всего можно обойтись без вспомогательной переменной res, воспользовавшись векторизированным решением - groupby.SeriesGroupBy.transform().

Пример:

In [85]: df = pd.DataFrame([[1, 2, 8], [1, 4, 5], [2, 10, 11], [2, 9, 13]], columns=["id", "v1", "v2"])

In [86]: df
Out[86]:
   id  v1  v2
0   1   2   8
1   1   4   5
2   2  10  11
3   2   9  13

In [87]: df["new"] = df.groupby("id")["v2"].transform("idxmax")

In [88]: df
Out[88]:
   id  v1  v2  new
0   1   2   8    0
1   1   4   5    0
2   2  10  11    3
3   2   9  13    3

NOTE: комментарии по типу "ваш код не работает" / "у меня возникает ошибка" / etc. не принимаются без воспроизводимого примера данных в вопросе. ?

→ Ссылка
Автор решения: MaxU

Ответ на уточненный вопрос с приведенным примером данных:

res = df.merge(df.groupby("Name").sum().idxmax(axis=1).reset_index(name="num"), how="left")

результат:

In [112]: res
Out[112]:
      Name  Ноябрь  Декабрь  Февраль      num
0  Алексей      15       10       15   Ноябрь
1  Алексей      10       10       10   Ноябрь
2   Андрей      15       25       15  Февраль
3  Алексей      15       15       10   Ноябрь
4   Андрей      25       10       45  Февраль
→ Ссылка