R Расширить данные временного ряда на основе начальной и конечной точки - PullRequest
0 голосов
/ 04 августа 2020

Думаю, у меня довольно простая просьба. У меня есть следующий фрейм данных, где «место» - это уникальный идентификатор, а start_date и end_date могут перекрываться. Значения уникальны для каждого идентификатора «места».

place  start_date   end_date value
1     2007-09-01  2010-10-12  0.5
2     2013-09-27  2015-10-11  0.7
...

Мне нужно создать переменную на основе года, в которой я расширяю временной ряд на каждый год (начиная с первого января (т.е. -01-01) начинает новую строку для этого конкретного "места" и "значения". Я имею в виду что-то вроде этого:

place  year  value 
1     2007    0.5   
1     2008    0.5   
1     2009    0.5   
1     2010    0.5   
2     2013    0.7    
2     2014    0.7    
2     2015    0.7    
...

Есть некоторые случаи с перекрытием (ie. "Place" = 1 & "год" = 2007) для двух отдельных случаев, когда одно наблюдение начинается с одного года, а другое наблюдение продолжается с этого года. В этом случае я бы предпочел "значение", которое заканчивается этим указанным c годом. Итак если одно наблюдение для place = 1 заканчивается 2007 годом в марте, а другое place = 1 начинается с 2007 в апреле, значение year = 2007 для place = 1 будет отмечено предыдущим «конечным» значением, если это имеет смысл.

Я дошел только до этого: данные библиотеки (data.table) <- data.table (dat) data [, <code>:= (start_date = as.Date (start_date), end_date = as.Date (end_date)) ] data [, num_mons: = length (seq (from = start_date, to = end_date, by = 'y ear ')), by = 1: nrow (data)]

Думаю, написание al oop имеет наибольший смысл?

Спасибо за вашу помощь и совет.

Ответы [ 2 ]

1 голос
/ 08 августа 2020

Вы можете сделать следующее:

library(lubridate)
library(tidyverse)
df %>%
  group_by(place) %>%
  mutate(year = list(seq(year(ymd(start_date)), year(ymd(end_date)))))%>%
  unnest(year)%>%
  select(place,year,value)

# A tibble: 7 x 3
# Groups:   place [2]
  place  year value
  <int> <int> <dbl>
1     1  2007   0.5
2     1  2008   0.5
3     1  2009   0.5
4     1  2010   0.5
5     2  2013   0.7
6     2  2014   0.7
7     2  2015   0.7
1 голос
/ 08 августа 2020

Использование решения tidyverse может выглядеть так:

library(dplyr)
library(stringr)
library(purrr)
library(tidyr)

data <- tibble(place = c(1, 2),
               start_date = c('2007-09-01',
                              '2013-09-27'),
               end_date = c('2010-10-12',
                            '2015-10-11'),
               value = c(0.5, 0.7))

data %>%
  mutate(year = map2(start_date,
                     end_date,
                     ~ as.character(str_extract(.x, '\\d{4}'): 
                                    str_extract(.y, '\\d{4}')))) %>%
  separate_rows(year) %>%
  filter(!year %in% c('c', '')) %>%
  select(place, year, value)

#   place year  value
#   <dbl> <chr> <dbl>
# 1     1 2007    0.5
# 2     1 2008    0.5
# 3     1 2009    0.5
# 4     1 2010    0.5
# 5     2 2013    0.7
# 6     2 2014    0.7
# 7     2 2015    0.7

У меня проблемы с пониманием третьего абзаца вашего вопроса («Есть ...»). Мне кажется, это отдельный вопрос. Если это так, рассмотрите возможность переноса вопроса в отдельный пост здесь, на SO. Если это не отдельный вопрос, пожалуйста, переформулируйте абзац.

...