Все столбцы не передаются, когда мы используем применить к результату groupby с настраиваемой функцией

Создайте DataFrame,

x_df = pd.DataFrame({'a': [1,2,3,4,5,6], 'b': [1,2,1,2,1,2],
                     'c': ['x','x','y','y','z','z']})

Out[56]: 
   a  b  c
0  1  1  x
1  2  2  x
2  3  1  y
3  4  2  y
4  5  1  z
5  6  2  z

Теперь я хочу использовать функцию для каждого значения столбца «c». Поэтому я использую функцию apply() для результата groupby.

x_df = pd.DataFrame({'a': [1,2,3,4,5,6], 'b': [1,2,1,2,1,2], 'c': ['x','x','y','y','z','z']})

def fun(X):
    print("===============>>>>>>>>>>>>>>>>>>>>> ")
    print(list(X))
    print("\n")
    c_str = X.c.tolist[0]
    print("Value of c_str ==========>>> "+ str(c_str))
    return y


x_df1 = x_df.groupby('c').apply(fun).reset_index()

Выполнение приведенного выше кода дает следующий результат:

---------------------------------------------------------------
===============>>>>>>>>>>>>>>>>>>>>> 
['a', 'b', 'c']


===============>>>>>>>>>>>>>>>>>>>>> 
['a', 'b', 'c']


===============>>>>>>>>>>>>>>>>>>>>> 
**['a', 'b']**


===============>>>>>>>>>>>>>>>>>>>>> 
**['a', 'b']**


Traceback (most recent call last):

  File "<ipython-input-20-6870c2554589>", line 12, in <module>
    x_df1 = x_df.groupby('c').apply(fun).reset_index()

  File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\core\groupby\groupby.py", line 930, in apply
    return self._python_apply_general(f)

  File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\core\groupby\groupby.py", line 936, in _python_apply_general
    self.axis)

  File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\core\groupby\groupby.py", line 2273, in apply
    res = f(group)

  File "<ipython-input-20-6870c2554589>", line 6, in fun
    c_str = X.c.tolist[0]

  File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\core\generic.py", line 4376, in __getattr__
    return object.__getattribute__(self, name)

AttributeError: 'DataFrame' object has no attribute 'c'

Итак, в первых двух вызовах функции fun X есть все три столбца (что и должно быть), но в 3-м и 4-м столбце вызова c отсутствует. из-за чего я не могу получить к нему доступ. Может ли кто-нибудь объяснить мне, что я делаю не так, и почему столбец c отсутствует на 3-м и 4-м вызовах?

У вас есть синтаксические ошибки повсюду в вашем вопросе

user3483203 10.12.2018 03:16

Приносим извинения за ошибки,

Gautam Kumar 10.12.2018 03:41
Почему в Python есть оператор "pass"?
Почему в Python есть оператор "pass"?
Оператор pass в Python - это простая концепция, которую могут быстро освоить даже новички без опыта программирования.
Некоторые методы, о которых вы не знали, что они существуют в Python
Некоторые методы, о которых вы не знали, что они существуют в Python
Python - самый известный и самый простой в изучении язык в наши дни. Имея широкий спектр применения в области машинного обучения, Data Science,...
Основы Python Часть I
Основы Python Часть I
Вы когда-нибудь задумывались, почему в программах на Python вы видите приведенный ниже код?
LeetCode - 1579. Удаление максимального числа ребер для сохранения полной проходимости графа
LeetCode - 1579. Удаление максимального числа ребер для сохранения полной проходимости графа
Алиса и Боб имеют неориентированный граф из n узлов и трех типов ребер:
Оптимизация кода с помощью тернарного оператора Python
Оптимизация кода с помощью тернарного оператора Python
И последнее, что мы хотели бы показать вам, прежде чем двигаться дальше, это
Советы по эффективной веб-разработке с помощью Python
Советы по эффективной веб-разработке с помощью Python
Как веб-разработчик, Python может стать мощным инструментом для создания эффективных и масштабируемых веб-приложений.
2
2
110
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Ответ принят как подходящий

Проблема здесь:

c_str = X.c.tolist[0]

pd.Series.tolist - это метод. Для вызова метода используйте круглые скобки:

c_str = X.c.tolist()[0]

Также, конечно, убедитесь, что вы определили y.

Еще он возвращает y, который появляется из ниоткуда.

user3483203 10.12.2018 03:22

Согласитесь, что вопрос непонятный. Ошибка также возникает при предложенном вами изменении. Если бы проблема была вызвана вызовом функции, он бы получил TypeError, «объект функции не подлежит подписке»

user3483203 10.12.2018 03:31

@ user3483203, Странно, у меня отлично работает на Pandas v0.23.0 / Python 3.6.5. Вы получаете обычную первую группу, пройденную дважды (из-за того, как работает groupby + apply), но в остальном ошибок нет.

jpp 10.12.2018 03:33
repl.it/repls/ElementaryMotionlessApplicationstack Может быть, что-то введено в 0.23.4
user3483203 10.12.2018 03:34

@ user3483203, попробуйте return None или return 1 вместо return y. Если определен y, ошибки не возникает. Я думаю, что там какая-то странная логика обработки ошибок Pandas.

jpp 10.12.2018 03:38

Я постараюсь ответить на ваш вопрос, но сначала я вижу несколько проблем с вашим сообщением, поэтому я хотел бы указать на них:

  1. Ваше форматирование испорчено, и вам очень трудно читать ваш код.
  2. Ваша функция fun НЕ определяет переменную, которую вы пытаетесь вернуть: y.
  3. Ваш вопрос НЕ объясняет, в чем заключается первоначальная проблема. Вы спрашиваете, почему ваш код неправильный, вместо того, чтобы правильно решить вашу проблему.

Согласно вашему вопросу, вы хотите использовать функцию применения для каждой строки в C, но группировка по c может удалить некоторые строки. Итак, вы можете попробовать

def fun(X):
    return X.c.tolist()[0]

x_df1 = x_df['c'].apply(fun)

Но проблему можно решить и лучше. Вместо передачи сгруппированного объекта вы можете просто передать вектор-столбец:

x_df1 = x_df['c'].apply(fun)

Однако, если бы мы знали исходную проблему, которую вы пытаетесь решить, я бы порекомендовал применить лямбда-вызов:

x_df1 = x_df['c'].apply(lambda x: list(x))

Я использовал list(), но его следует заменить на то, что вы пытаетесь сделать.

Другие вопросы по теме