data.table: (быстро) установить значения столбца в группе в последний элемент группы - PullRequest
0 голосов
/ 04 мая 2020

Скажите, что у меня есть такой набор данных:

 example <- data.table(Object = rep(LETTERS[1:3], each=3), date = as.Date(rep(c(NA,NA,"2020-01-01"),3)), date_data =1:9)

example
   Object       date date_data
1:      A       <NA>         1
2:      A       <NA>         2
3:      A 2020-01-01         3
4:      B       <NA>         4
5:      B       <NA>         5
6:      B 2020-01-01         6
7:      C       <NA>         7
8:      C       <NA>         8
9:      C 2020-01-01         9

Я бы хотел установить все date_data в определенной группе равными последнему значению date_data для этой группы. Итак, желаемый результат такой:

   Object       date date_data
1:      A       <NA>         3
2:      A       <NA>         3
3:      A 2020-01-01         3
4:      B       <NA>         6
5:      B       <NA>         6
6:      B 2020-01-01         6
7:      C       <NA>         9
8:      C       <NA>         9
9:      C 2020-01-01         9

Теперь мне удалось получить именно то, что мне нужно, используя example[, date_data:= .SD[.N]$date_data, by = "Object"]. Проблема в том, что я хочу сделать такой вызов в al oop итерации по большой таблице данных. Вызов .SD каждый раз слишком медленный . В идеале код должен использовать .I (например, здесь ) или некоторые другие оптимизированные для data.table функции, о которых я не знаю. Мне не удалось найти правильный способ сделать это.

Есть идеи?

1 Ответ

3 голосов
/ 04 мая 2020

Вы можете использовать data.table::last:

library(data.table)

example <- data.table(
  Object = rep(LETTERS[1:3], each=3),
  date = as.Date(rep(c(NA,NA,"2020-01-01"),3)), 
  date_data =1:9
)
example[, date_data := last(date_data), by =  Object ]
example
#    Object       date date_data
#    <char>     <Date>     <int>
# 1:      A       <NA>         3
# 2:      A       <NA>         3
# 3:      A 2020-01-01         3
# 4:      B       <NA>         6
# 5:      B       <NA>         6
# 6:      B 2020-01-01         6
# 7:      C       <NA>         9
# 8:      C       <NA>         9
# 9:      C 2020-01-01         9

Но я не знаю, есть ли оптимизация, иначе вы можете просто использовать .N в переменной:

example[, date_data := date_data[.N], by =  Object]
example
...