我有下表。
dt = data.table(id = 1:5, intMask = c(11,14,8,1,13), imprint = c("1011", "1110", "1000", "0001", "1101"), N = c(3,3,1,1,3), mass = c(.05,.1,.15,.3,.4))
id intMask imprint N mass
1: 1 11 1011 3 0.05
2: 2 14 1110 3 0.10
3: 3 8 1000 1 0.15
4: 4 1 0001 1 0.30
5: 5 13 1101 3 0.40
假设
imprint
列表示一个集合的二进制表示(即这里我们有基数为 5 的集合的子集)。 intMask
表示对应于二进制表示的各个整数。 N
各自的基数 - 即表示中 1 的数量。
我想通过对对应于各个超集的所有行求和来更新 sum
。我建议使用 bitwAnd()
函数和 intMask
列来有效地找到相应的超集。
for(i in 1:nrow(dt)) {
i.intMask <- dt[i,intMask]
i.N <- dt[i,N]
dt[i, newMass := sum(dt[N >= i.N,][bitwAnd(intMask, i.intMask) == i.intMask, mass])]
}
即得到
dt[]
id intMask imprint N mass newMass
1: 1 11 1011 3 0.05 0.05
2: 2 14 1110 3 0.10 0.10
3: 3 8 1000 1 0.15 0.70
4: 4 1 0001 1 0.30 0.75
5: 5 13 1101 3 0.40 0.04
假设有数千行。您知道如何有效地做到这一点吗?最好使用
data.table
更新?
这可能是一种选择
dt[
dt[dt,
c(
id = .(i.id),
newMass = .(mass * (bitwAnd(intMask, i.intMask) == i.intMask))
),
on = .(N >= N)
][, .(newMass = sum(newMass)), id],
on = "id"
]
这给出了
id intMask imprint N mass newMass
<int> <num> <char> <num> <num> <num>
1: 1 11 1011 3 0.05 0.05
2: 2 14 1110 3 0.10 0.10
3: 3 8 1000 1 0.15 0.70
4: 4 1 0001 1 0.30 0.75
5: 5 13 1101 3 0.40 0.40