У меня есть DataFrame с информацией о пользователях, такой как имя, почта, день рождения, жанр... но в фрейме данных есть дубликаты пользователей с важной различной информацией в обеих строках. Также проблема в том, что есть разные пользователи с одинаковым Именем. Например:
Исходный фрейм данных
Name Mail Birthday Genre Subscription Age Comments
0 A A@gmail.com 1-1-1990 M Y 33 -
1 B None NaT F N NaN -
2 C C@gmail.com 1-1-1985 M Y 38 -
3 D None 1-1-1980 I N 43 -
4 B None 1-1-1995 I N 27 -
5 D D@gmail.com NaT M Y NaN -
6 B B@gmail.com NaT I Y NaN -
7 C C2@gmail.com 1-1-1970 F N 53 -
И я хочу что-то вроде этого:
Name Mail Birthday Genre Subscription Age Comments
0 A A@gmail.com 1-1-1990 M Y 33 -
1 B B@gmail.com 1-1-1995 F Y 27 -
2 C C@gmail.com 1-1-1985 M Y 38 -
3 D D@gmail.com 1-1-1980 M Y 43 -
4 C2 C2@gmail.com 1-1-1970 F N 53 -
Можно, например, сгруппировать по имени и объединить строки, сохраняя всю информацию в одной строке, и если в обеих строках столбца имеют одинаковое значение, сохранить его. А также, если 2 строки с разными значениями имеют одинаковое имя, создайте строку для другого пользователя с новым именем.
Например промежуточный df:
Name Mail Birthday Genre Subscription Age Comments
0 A A@gmail.com 1-1-1990 M Y 33 -
1 B B@gmail.com 1-1-1995 F Y 27 -
2 C [C@gmail.com, [1-1-1985, [M, [Y, [38, [-,
C2@gmail.com] 1-1-1970] F] N] 53] -]
3 D D@gmail.com 1-1-1980 M Y 43 -
Я пробовал использовать функцию groupby или функцию соединения, но у меня это не сработало.
Спасибо.
Вы можете комбинировать значения с заменой значений для каждого столбца для исключения с агрегированием по всем столбцам без Name с помощью пользовательской функции с повторным использованием переменной с помощью оператора walrus := с преобразованием списков элементов ene в скаляры и пустых списков после удаления отсутствующих значений и дубликатов в NaNs:
f = lambda x: y if (len(y:=list(dict.fromkeys(x.dropna()))) > 1)
else y[0]
if len(y) != 0
else np.nan
df = (df.replace({'Mail':{'None':np.nan},
'Birthday':{'NaT':np.nan},
'Genre':{'I':np.nan},
'Subscription':{'N':np.nan}})
.set_index('Name')
.groupby('Name')
.agg(f))
print (df)
Mail Birthday Genre Subscription \
Name
A A@gmail.com 1-1-1990 M Y
B B@gmail.com 1-1-1995 F Y
C [C@gmail.com, C2@gmail.com] [1-1-1985, 1-1-1970] [M, F] Y
D D@gmail.com 1-1-1980 M Y
Age Comments
Name
A 33.0 -
B 27.0 -
C [38.0, 53.0] -
D 43.0 -
Можете ли вы поделиться кодом, который вы написали, чтобы попытаться достичь этого результата? Итак, мы можем развить вашу текущую попытку?