I just want to take difference between rows in a data.table such that dif[n] = value[n] - value[n-1].
I currently try to achive that using zoo::rollapplyr
:
library(data.table)
dt <- fread(text = "#
variable value
xyz 3
xyz 7
xyz 5
abc 9
abc 10
abc 2
")
dt[, dif := zoo::rollapplyr(value, 2, function(x){r <- diff(x,lag = 1)}, align = "right"), by = list(variable)]
#> dt
#> variable value dif
#> 1: xyz 3 4
#> 2: xyz 7 -2
#> 3: xyz 5 4
#> 4: abc 9 1
#> 5: abc 10 -8
#> 6: abc 2 1
But, compared to what I have, the results should be shifted by 1 position, and the first position for each "variable" should be NA, i.e. dif
should be c(NA, 4, -2, NA, 1, -8)
. The first value for each "variable should be NA because there is no position n-1. Any idea how I can modify the function to accomplish this? Would really like to know how I can do this with rollapplyr for the sake of my own understanding.
EDIT 2024: data.table
prevents the unwanted recycling of the generated dif
values by failing with this error message:
Error in `[.data.table`(dt, , `:=`(dif, zoo::rollapply(value, 2, function(x) { :
Supplied 2 items to be assigned to group 1 of size 3 in column 'dif'. The RHS length must either be 1 (single values are ok) or match the LHS length exactly. If you wish to 'recycle' the RHS please use rep() explicitly to make this intent clear to readers of your code.
value
– Sinker