Как суммировать и суммировать в Python (или R) с определенным условием c - PullRequest
2 голосов
/ 03 марта 2020

Цель

У меня есть набор данных df, который я хотел бы сгруппировать в столбец длины, взять его сумму и отобразить время окончания, которое с ним связано:

 length start                      end                      duration
 6330   12/17/2019 10:34:23 AM     12/17/2019 10:34:31 AM   8
 57770  12/19/2019 5:19:56 PM      12/17/2019 5:24:19 PM    263
 6330   12/17/2019 10:34:54 AM     12/17/2019 10:35:00 AM   6
 6330   12/18/2019 4:36:44 PM      12/18/2019 4:37:13 PM    29
 57770  12/19/2019 5:24:47 PM      12/19/2019 5:26:44 PM    117

Желаемый выход

length  end                     total Duration
6330    12/18/2019 4:37:13 PM   43  
57770   12/19/2019 5:26:44 PM   380 

Dput

structure(list(length = c(6330L, 57770L, 6330L, 6330L, 57770L
), start = structure(c(1L, 4L, 2L, 3L, 5L), .Label = c("12/17/2019 10:34:23 AM", 
"12/17/2019 10:34:54 AM", "12/18/2019 4:36:44 PM", "12/19/2019 5:19:56 PM", 
"12/19/2019 5:24:47 PM"), class = "factor"), end = structure(c(1L, 
3L, 2L, 4L, 5L), .Label = c("12/17/2019 10:34:31 AM", "12/17/2019 10:35:00 AM", 
"12/17/2019 5:24:19 PM", "12/18/2019 4:37:13 PM", "12/19/2019 5:26:44 PM"
), class = "factor"), duration = c(8L, 263L, 6L, 29L, 117L)), class = "data.frame", row.names =    c(NA, 
-5L))

Это то, что я пробовал :, но как мне это сделать? также отобразить конечный столбец, который связан с «последним» значением длины? Например, длина 6330 имеет 3 конечных значения, к которым прикреплены 3 длительности:

           12/17/2019 10:34:31 AM            8
           12/17/2019 10:35:00 AM            6
           12/18/2019 4:37:13 PM            29


12/18/2019 4:37:13 PM is the latest end time, so I would like to output the end time, 
along with the sum of durations for this particular length value. 

Требуемый вывод

length  end                     total Duration
6330    12/18/2019 4:37:13 PM   43  
57770   12/19/2019 5:26:44 PM   380 

Вот что Я пытался:

import pandas as pd
import numpy as np

df1 = df.groupby('length')['duration'].sum()

Однако, это только выводит длину и общую продолжительность. Как бы я вывел длину, последний конец, а также общую продолжительность для этой конкретной длины?

Любая помощь приветствуется.

Ответы [ 3 ]

3 голосов
/ 03 марта 2020

Pandas мы можем использовать GroupBy.agg для этого, но у нас есть два варианта:

  1. простая агрегация словарей:
df.groupby('length').agg({'duration': 'sum', 'end': 'max'}).reset_index()

   length  duration                 end
0    6330        43 2019-12-18 16:37:13
1   57770       380 2019-12-19 17:26:44

Именованное агрегирование s, переименование столбцов при агрегировании:

новое с pandas 0.25.0+

df.groupby('length').agg(
    end=('end', 'max'),
    total_duration=('duration', 'sum')
).reset_index()

   length                 end  total_duration
0    6330 2019-12-18 16:37:13              43
1   57770 2019-12-19 17:26:44             380

Примечание: не забудьте преобразовать столбцы даты в datetime до:

df[['start', 'end']] = (
    df[['start', 'end']].apply(lambda x: pd.to_datetime(x, infer_datetime_format=True))
)
3 голосов
/ 03 марта 2020

В R мы можем сгруппировать по «длине», использовать summarise, получить sum «продолжительности» и извлечь элемент max «конца» после преобразования в класс DateTime с mdy_hms (от lubridate)

library(dplyr)
library(lubridate)
df %>%
   group_by(length) %>% 
   summarise(duration = sum(duration), end = end[which.max(mdy_hms(end))])
2 голосов
/ 03 марта 2020

В R это можно сделать с помощью некоторых библиотек tidyverse:

library(tidyverse)

df <- tribble(
~length,~start,~end,~duration,
6330,"12/17/2019 10:34:23 AM","12/17/2019 10:34:31 AM",8,
57770,"12/19/2019 5:19:56 PM","12/17/2019 5:24:19 PM",263,
6330,"12/17/2019 10:34:54 AM","12/17/2019 10:35:00 AM",6,
6330,"12/18/2019 4:36:44 PM","12/18/2019 4:37:13 PM",29,
57770,"12/19/2019 5:24:47 PM","12/19/2019 5:26:44 PM",117
) %>% 
  mutate_at(
    vars(start, end),
    lubridate::mdy_hms
  )

df %>% 
  group_by(length) %>% 
  summarise(
    end = max(end, na.rm = TRUE),
    duration = sum(duration, na.rm = TRUE)
  )

Предоставление:

# A tibble: 2 x 3
  length end                 duration
   <dbl> <dttm>                 <dbl>
1   6330 2019-12-18 16:37:13       43
2  57770 2019-12-19 17:26:44      380

Метки времени отформатированы в формате ISO.

Я использовал TZ по умолчанию (UT C) при преобразовании значений.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...