Background
I've a quarterly data set where certain quarters and corresponding values are missing. The characteristics of the data set are:
- Each group should have the same number of quarters but in practe quarters are missing
- For missing quarter values are unknown
- This is to be resolved by sourcing imputing next available value; for instance, as available via
na.locffunction
- This is to be resolved by sourcing imputing next available value; for instance, as available via
Example data
# Packages
Vectorize(require)(package = c("tidyverse", "zoo", "magrittr"),
character.only = TRUE)
# Seed
set.seed(123)
# Dummy data
dta <- data.frame(group = rep(LETTERS[1:5], 10)) %>%
group_by(group) %>%
mutate(qrtr = seq(
from = as.Date("01/01/2012", "%d/%m/%Y"),
to = as.Date("31/5/2014", "%d/%m/%Y"),
by = "quarter"
)) %>%
ungroup() %>%
mutate(qrtr = as.yearqtr(qrtr)) %>%
arrange(group, qrtr) %>%
mutate(value = sample(1:10, 50, replace = TRUE))
# Remove random rows
dta[sample(1:dim(dta)[1], 10), c(2, 3)] <- NA
dta %<>% na.omit()
Preview
# A tibble: 40 x 3
group qrtr value
<chr> <S3: yearqtr> <int>
1 A 2012 Q1 3
2 A 2012 Q2 8
3 A 2012 Q4 9
4 A 2013 Q1 10
5 A 2013 Q3 6
6 A 2013 Q4 9
7 A 2014 Q1 6
8 B 2012 Q1 10
9 B 2012 Q2 5
10 B 2012 Q3 7
# ... with 30 more rows
Problem
Create add rows within each group where quarter are missing. Total number of quarter is derived from sequence
min(qrtr)tomax(qrtr), in the context of existing code:seq(from = as.Date("01/01/2012", "%d/%m/%Y"), to = as.Date("31/5/2014", "%d/%m/%Y"), by = "quarter")First non-missing value should be carried forward for the missing value.
Desired results:
>> dta
# A tibble: 50 x 3
group qrtr value
<chr> <S3: yearqtr> <int>
1 A 2012 Q1 3
2 A 2012 Q2 8
3 A 2012 Q3 8
4 A 2012 Q4 9
5 A 2013 Q1 10
6 A 2013 Q2 10
7 A 2013 Q3 6
8 A 2013 Q4 9
9 A 2014 Q1 6
10 A 2015 Q1 6
# ... with 40 more rows
Proposed approaches
One approach would rely on making use of the expand, in order to convert implicitly missing values to explicitly missing values. This so far creates missing quarters but there is no clear way of creating missing observations for value column for where given quarter is missing.
dta %>%
# Append mixing quarters
expand(group, qrtr) %>%
left_join(data.frame(qrtr = as.yearqtr(
seq(
from = as.Date("01/01/2012", "%d/%m/%Y"),
to = as.Date("31/5/2014", "%d/%m/%Y"),
by = "quarter"
)
)), by = "qrtr") %>%
# TODO
# mutate(value = na.locf(value)) %>%
arrange(group, qrtr) -> dta_fixed