кончил со средним питоном - PullRequest
0 голосов
/ 15 мая 2018

У меня есть pd.DataFrame, как показано ниже,

Hr    Name       Count       Day
6    1318       10.0        Friday     
7    1318       20.0        Friday     
8    1318       2.0         Friday     
9    1318       18.0        Friday        
6    1318       2.0         Monday
7    1318       15.0        Monday
8    1318       2.0         Monday
9    1318       5.0         Monday
6    1319       20.0        Friday     
7    1319       30.0        Friday     
8    1319       50.0        Friday     
9    1319       5.0         Friday     
6    1319       3.0         Monday
7    1319       30.0        Monday
8    1319       2.0         Monday
9    1319       5.0         Monday

Я хочу повторить каждое Подсчет и суммировать имя, а затем сделать 1, если значение> = 20. наконец посчитайте значения, сколько раз достигнуто выше> = 20. Когда сумма Count достигла> = 20, тогда следующее значение должно быть посчитано с фактическим значением.

Ожидаемый ОП:

[{'Friday' :[2,3],'Monday':[1,1]}]

Вот как сделать в пятницу:

1318Friday[10+20=30 30 >=20 so 1, 2+18 =20 again 1, Total is 2]
1319Friday[20 20 >=20 so 1, 30 again 1,50 again 1,5 is !>=20, Total is 3]
Finally {'Friday' : [2,3]}

Код, который я пробовал:

finalresult = [data]
df = pd.DataFrame(finalresult)
df['csum'] = df.groupby(['Day','Name'])['Count'].cumsum()

Ответы [ 2 ]

0 голосов
/ 15 мая 2018

Сначала создайте текущий счетчик дней:

df['running'] = (df.Day != df.Day.shift(1)).cumsum()
>>> df
    Hr  Name    Count   Day running
0   6   1318    10.0    Friday  1
1   7   1318    20.0    Friday  1
2   8   1318    2.0 Friday  1
3   9   1318    18.0    Friday  1
4   6   1318    2.0 Monday  2
5   7   1318    15.0    Monday  2
6   8   1318    2.0 Monday  2
7   9   1318    5.0 Monday  2
8   6   1319    20.0    Friday  3
9   7   1319    30.0    Friday  3
10  8   1319    50.0    Friday  3
11  9   1319    5.0 Friday  3
12  6   1319    3.0 Monday  4
13  7   1319    30.0    Monday  4
14  8   1319    2.0 Monday  4
15  9   1319    5.0 Monday  4

Это позволит вам группировать по нему.

Теперь (к сожалению) создайте функцию для подсчета количества более 20:

def count_counts(g):
    s, c = 0, 0
    for e in g:
        s += e
        if s > 20:
            s, c = 0, c + 1
    return c

сгруппируйте по дням и дням и примените его, затем сгруппируйте по дням и перечислите результаты:

cc = df.Count.groupby([df.Day, df.running]).apply(count_counts).reset_index()
>>> cc.Count.groupby(cc.Day).apply(list)
Day
Friday    [1, 2]
Monday    [1, 1]
Name: Count, dtype: object
0 голосов
/ 15 мая 2018

Вы можете сделать это с помощью apply пользовательской функции для сгруппированных данных.

## custom function
def get_cumsum(x):

    adds = 0
    counter = 0
    for i in x:
        counter += i
        if counter >= 20:
            adds += 1
            counter=0
    return adds 

## apply the function to dataframe
df1 = df.groupby(['Name','Day'])['Count'].apply(get_sum).reset_index()

## get dict 
df1.groupby('Day')['Count'].apply(list).to_dict()     
{'Friday': [2, 3], 'Monday': [1, 1]}

Пояснение:

  1. Функция сбрасывается каждый раз, когда сумма достигает> = 20, и снова начинает считать
  2. Мы применяем эту функцию к сгруппированным данным, чтобы найти информацию для каждого дня и имени.
  3. Наконец, мы конвертируем результат из шага 2 в dict, чтобы получить желаемый результат.
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...