#r
#r
Вопрос:
Допустим, у меня есть фрейм данных, который выглядит следующим образом:
ID Year Value Value_Prior.Year
aaa 2010 800
bbb 2010 1000
ccc 2010 900
ccc 2010 400
aaa 2011 400
bbb 2011 300
ccc 2011 100
bbb 2013 100
Я хочу заполнить столбец «Предыдущий год», сопоставив ID и Year — 1. Я хотел бы выполнить суммирование всех других записей, которые соответствуют идентификатору и году — 1, на случай, если они не уникальны. Я создал цикл for, который будет работать, но, учитывая размер фактических данных, я пытаюсь найти более быстрый вариант.
РЕДАКТИРОВАТЬ: может отсутствовать несколько лет и несколько дубликатов. Итак, в приведенном выше примере последнее «Value_Prior.»Year» должно быть NA, а предпоследним значением должна быть сумма, или 1300.
Спасибо!
Комментарии:
1. Попробуйте с
lag
после группировки по ‘ID’, т.е.library(dplyr); df1 %>% group_by(ID) %>% mutate(Value_Prior = lag(Value))
2. Добавлено редактирование для уточнения, проблема с решением задержки заключается в том, что может отсутствовать несколько лет
Ответ №1:
Вот однострочный вариант, использующий только базу R.
transform(DF, PriorYearValue = ave(Value, ID, FUN = function(x) c(NA, head(x, -1))))
предоставление:
ID Year Value PriorYearValue
1 aaa 2010 800 NA
2 bbb 2010 1000 NA
3 ccc 2010 900 NA
4 aaa 2011 400 800
5 bbb 2011 300 1000
6 ccc 2011 100 900
Примечание
Предполагается, что входные данные в воспроизводимой форме являются:
Lines <- "
ID Year Value
aaa 2010 800
bbb 2010 1000
ccc 2010 900
aaa 2011 400
bbb 2011 300
ccc 2011 100"
DF <- read.table(text = Lines, header = TRUE, strip.white = TRUE)
Обновить
Что касается редактирования, которое было добавлено к вопросу, сложные соединения легко выполняются в SQL, поэтому:
Lines <- '
ID Year Value
aaa 2010 800
bbb 2010 1000
ccc 2010 900
ccc 2010 400
aaa 2011 400
bbb 2011 300
ccc 2011 100
bbb 2013 100'
DF <- read.table(text = Lines, header = TRUE, strip.white = TRUE)
library(sqldf)
sqldf("select a.*, sum(b.Value) PrevYearValue
from DF a
left join DF b on a.ID = b.ID and a.Year - 1 = b.Year
group by a.rowid")
предоставление:
ID Year Value PrevYearValue
1 aaa 2010 800 NA
2 bbb 2010 1000 NA
3 ccc 2010 900 NA
4 ccc 2010 400 NA
5 aaa 2011 400 800
6 bbb 2011 300 1000
7 ccc 2011 100 1300
8 bbb 2013 100 NA
Комментарии:
1. Извините, добавлено редактирование для уточнения. Некоторые годы могут отсутствовать, а другие записи могут быть не уникальными, поэтому мне нужно сопоставить как год, так и идентификатор и выполнить суммирование
2. Смотрите обновление, добавленное в конце.
3. Отлично — спасибо!