I have data
dat1 <- data.table(id=1:9,
                   group=c(1,1,2,2,2,3,3,3,3),
                   t=c(14,17,20,21,26,89,90,95,99),
                   index=c(1,2,1,2,3,1,2,3,4)
                  )
and I would like to compute the difference on t to the previous value, according to index. For the first instance of each group, I would like to compute the difference to some external variable 
dat2 <- data.table(group=c(1,2,3),
                   start=c(10,15,80)
                  )
such that the following result should be obtained:
> res 
   id group  t index dif
1:  1     1 14     1   4
2:  2     1 17     2   3
3:  3     2 20     1   5
4:  4     2 21     2   1
5:  5     2 26     3   5
6:  6     3 89     1   9
7:  7     3 90     2   1
8:  8     3 95     3   5
9:  9     3 99     4   4
I have tried using
dat1[ , ifelse(index == min(index), dif := t - dat2$start, dif := t - t[-1]), by = group]
but I was unsure about referencing other elements of the same group and external elements in one step. Is this at all possible using data.table?
A possible solution:
dat1[, dif := ifelse(index == min(index),
                     t - dat2$start[match(.BY, dat2$group)],
                     t - shift(t))
     , by = group][]
which gives:
id group t index dif 1: 1 1 14 1 4 2: 2 1 17 2 3 3: 3 2 20 1 5 4: 4 2 21 2 1 5: 5 2 26 3 5 6: 6 3 89 1 9 7: 7 3 90 2 1 8: 8 3 95 3 5 9: 9 3 99 4 4
Or a variant as proposed by @jogo in the comments which avoids the ifelse:
dat1[, dif := t - shift(t), by = group
     ][index == 1, dif := t - dat2[group==.BY, start], by = group][]
                        If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With