2015-09-27 3 views
1

У меня есть два data.tables, и у одного есть подмножество строк/столбцов другого. Я хотел бы, чтобы увеличить значения большего data.table на 1 для каждого ненулевого значения в меньшей таблице:Увеличение значения data.table на основе другого значения data.table

DT1 <- as.data.table(matrix(c(0, 1, 2, 3), nrow=2, ncol=2, 
     dimnames=list(c("a", "b"), c("a", "b"))), keep=T) 
DT2 <- as.data.table(matrix(c(0, 0, 1, 2, 2, 1, 1, 0, 3), nrow=3, ncol=3, 
     dimnames=list(c("a", "b", "c"), c("a", "b", "c"))), keep=T) 

DT1 
# rn a b 
#1: a 0 2 
#2: b 1 3 
DT2 
# rn a b c 
#1: a 0 2 1 
#2: b 0 2 0 
#3: c 1 1 3 

Я хотел бы, чтобы увеличить значения в СД2, так что я получаю

# rn a b c 
#1: a 0 3 1 
#2: b 1 3 0 
#3: c 1 1 3 

(Это похоже на мой предыдущий вопрос о добавлении DT1 и dT2: Adding values in two data.tables ... Мне нужно сделать так :))

ответ

4

Другой способ:

require(data.table) # v1.9.6+ 
xcols = c("a", "b") 
icols = paste0("i.", xcols) # "i.*" to refer to DT1's cols 
DT2[DT1, (xcols) := Map(function(x, y) x + (y > 0L), mget(xcols), mget(icols)), on="rn"] 

Как это должно выглядеть следующим образом:

DT2[DT1, (xcols) := Map(function(x, y) x + (y > 0L), .SD, i.SD), .SDcols=xcols, i.SDcols = icols] 

или даже лучше было бы:

DT2[DT1, (xcols) := .SD + (i.SD > 0L), .SDcols=xcols, i.SDcols=icols] 
+0

Я немного смущен Вторая часть. Первая часть кода отлично работает. «Случай лучше» выглядит чисто, и я хотел бы написать его так, но я получаю «неиспользуемый аргумент (i.SDcols = icols)», когда я это делаю. – Stan

+1

Это потому, что он еще не реализован. – Arun

2

Я бы рассмотреть что-то вроде ...

inc_em <- with(melt(DT1)[value != 0], split(rn, variable)) 

for (k in names(inc_em)) 
    DT2[.(rn = inc_em[[k]]), (k) := get(k) + 1, on="rn" ] 

# rn a b c 
# 1: a 0 3 1 
# 2: b 1 3 0 
# 3: c 1 1 3