Создание функции для перебора DataFrame - PullRequest
0 голосов
/ 01 октября 2018

У меня проблема с созданием функции, которая распознает, находится ли конкретное значение в столбце между двумя значениями.

def bid(x):
if df['tla'] < 85000:
    return 1
elif (df['tla'] >= 85000) & (df['tla'] < 110000):
    return 2
elif (df['tla'] >= 111000) & (df['tla'] < 126000):
    return 3
elif (df['tla'] >= 126000) & (df['tla'] < 150000):
    return 4
elif (df['tla'] >= 150000) & (df['tla'] < 175000):
    return 5
elif (df['tla'] >= 175000) & (df['tla'] < 200000):
    return 6
elif (df['tla'] >= 200000) & (df['tla'] < 250000):
    return 7
elif (df['tla'] >= 250000) & (df['tla'] < 300000):
    return 8
elif (df['tla'] >= 300000) & (df['tla'] < 375000):
    return 9
elif (df['tla'] >= 375000) & (df['tla'] < 453100):
    return 10
elif df['tla'] >= 453100:
    return 11

Я применяю это к моей новой колонке:

df['bid_bucket'] = df['bid_bucket'].apply(bid)

И я получаю эту ошибку обратно:

ValueError: The truth value of a Series is ambiguous. Use a.empty, a.bool(), a.item(), a.any() or a.all().

У кого-нибудь есть идеи?

Ответы [ 5 ]

0 голосов
/ 01 октября 2018

Это уже можно выполнить с помощью pd.cut, определив края корзины и добавив +1 к меткам, чтобы ваша нумерация начиналась с 1.

import pandas as pd
import numpy as np
df = pd.DataFrame({'tla': [7, 85000, 111000, 88888, 51515151]})

df['bid_bucket'] = pd.cut(df.tla, right=False,
                          bins=[-np.inf, 85000, 110000, 126000, 150000, 175000,
                                200000, 250000, 300000, 375000, 453100, np.inf], 
                          labels=False)+1

Вывод: df

        tla  bid_bucket
0         7           1
1     85000           2
2    111000           3
3     88888           2
4    126000           4
5  51515151          11
0 голосов
/ 01 октября 2018

У вас есть две возможности.Либо примените функцию, определенную для строки в DataFrame pandas, построчно:

def function_on_a_row(row):
  if row.tla > ...
    ...

df.apply(function_on_a_row, axis=1)

В этом случае сохраните bid так, как вы его определили, но замените параметр x словом «»row ", а затем df с" row ", чтобы сохранить имя параметра значимым, и используйте:

df.bid_bucket = df.apply(bid, axis=1)

Или примените функцию, определенную для элемента серии Панд.

def function_on_an_elt(element_of_series):
  if element_of_series > ...
    ...

df.new_column = df.my_column_of_interest.apply(function_on_an_elt)

В вашем случае переопределите bid соответственно.

Здесь вы попытались смешать оба подхода, что не работает.

0 голосов
/ 01 октября 2018

Вы можете просто использовать функцию np.digitize , чтобы назначить диапазоны

df['bid_bucket'] = np.digitize(df['bid_bucket'],np.arange(85000,453100,25000))

Пример

a = np.random.randint(85000,400000,10)
#array([305628, 134122, 371486, 119856, 321423, 346906, 319321, 165714,360896, 206404])
bins=[-np.inf, 85000, 110000, 126000, 150000, 175000,
             200000, 250000, 300000, 375000, 453100, np.inf]
np.digitize(a,bins)

Out:

array([9, 4, 9, 3, 9, 9, 9, 5, 9, 7])

0 голосов
/ 01 октября 2018

Чтобы сохранить это в пандах: я думаю, что ссылка на df ['tla'] в вашей функции означает ссылку на серию, а не на одно значение, что приводит к неоднозначности.Вместо этого вы должны указать конкретное значение.Вы можете использовать лямбду-х, тогда ваш код может выглядеть примерно так:

df = pd.DataFrame({'tla':[10,123456,999999]})

def bid(x):
    if x < 85000:
        return 1
    elif (x >= 85000 and x < 110000):
        return 2
    elif (x >= 111000 and x < 126000):
        return 3
    elif (x >= 126000 and x < 150000):
        return 4
    elif (x >= 150000 and x < 175000):
        return 5
    elif (x >= 175000 and x < 200000):
        return 6
    elif (x >= 200000 and x < 250000):
        return 7
    elif (x >= 250000 and x < 300000):
        return 8
    elif (x >= 300000 and x < 375000):
        return 9
    elif (x >= 375000 and x < 453100):
        return 10
    elif x >= 453100:
        return 11

df['bid_bucket'] = df['tla'].apply(lambda x: bid(x))
df
0 голосов
/ 01 октября 2018

попробуйте следующее, используя numpy.select

import numpy as np

values = [1,2,3,4,5,6,7,8,9,10,11]
cond = [df['tla']<85000, (df['tla'] >= 850000) & (df['tla'] < 110000), .... ]

df['bid_bucket'] = np.select(cond, values)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...