Я не понимаю, почему apply
и transform
возвращают разные типы данных при вызове в том же фрейме данных. То, как я объяснял две функции себе, прежде чем что-то пошло «apply
, обрушивает данные, а transform
делает то же самое, что и apply
, но сохраняет исходный индекс и не рушится». Рассмотрим следующее.Pandas transform() vs apply()
df = pd.DataFrame({'id': [1,1,1,2,2,2,2,3,3,4],
'cat': [1,1,0,0,1,0,0,0,0,1]})
Давайте определить те id
S, которые имеют ненулевой элемент в столбце cat
.
>>> df.groupby('id')['cat'].apply(lambda x: (x == 1).any())
id
1 True
2 True
3 False
4 True
Name: cat, dtype: bool
Отлично. Однако, если бы мы хотели создать столбец индикаторов, мы могли бы сделать следующее.
>>> df.groupby('id')['cat'].transform(lambda x: (x == 1).any())
0 1
1 1
2 1
3 1
4 1
5 1
6 1
7 0
8 0
9 1
Name: cat, dtype: int64
Я не понимаю, почему DTYPE теперь int64
вместо булева возвращаемой функции any()
.
Когда я изменяю исходный фрейм данных, чтобы содержать некоторые булевы (обратите внимание, что нули остаются), подход преобразования возвращает логические значения в столбце object
. Это дополнительная тайна для меня, поскольку все значения являются логическими, но они указаны как object
, по-видимому, для соответствия dtype
исходного столбца смешанного типа целых чисел и булевых элементов.
df = pd.DataFrame({'id': [1,1,1,2,2,2,2,3,3,4],
'cat': [True,True,0,0,True,0,0,0,0,True]})
>>> df.groupby('id')['cat'].transform(lambda x: (x == 1).any())
0 True
1 True
2 True
3 True
4 True
5 True
6 True
7 False
8 False
9 True
Name: cat, dtype: object
Однако, когда я использую все логические значения, функция преобразования возвращает булевский столбец.
df = pd.DataFrame({'id': [1,1,1,2,2,2,2,3,3,4],
'cat': [True,True,False,False,True,False,False,False,False,True]})
>>> df.groupby('id')['cat'].transform(lambda x: (x == 1).any())
0 True
1 True
2 True
3 True
4 True
5 True
6 True
7 False
8 False
9 True
Name: cat, dtype: bool
Используя свои острые навыки распознавания образов, кажется, что dtype
результирующего столбца отражает структуру исходного столбца. Я был бы признателен за любые подсказки о том, почему это происходит или что происходит под капотом в функции transform
. Приветствия.
'apply' не разрушится данные. 'apply' является гибким и может возвращать серию или dataframe любого размера. 'transform' всегда сохраняет количество строк для каждой группы. 'transform' также отправляет каждый отдельный столбец в виде серии вызывающей функции. 'apply' отправляет весь файл данных в вызывающую функцию. –
[related] (http://stackoverflow.com/a/38579754/2336654) – piRSquared
Aha! Спасибо @piRSquared. Думаю, я понимаю, почему это происходит после прочтения этого комментария и изучения исходного кода. – 3novak