2017-05-02 50 views
0

我有2个data.table,我想用另一个按组来制作一个产品。2个数据表的排序产品

library(data.table)                                                 
set.seed(1)                                                   
DT <- as.data.table(matrix(rnorm(16),ncol=4))                                          
DT[,id:=c(1,1,2,2)]                                                 
DT2 <- as.data.table(matrix(rnorm(8),ncol=4))                                          
DT2[,id:=c(1,2)]                                                 

#DT 
#   V1   V2   V3   V4 id 
#1: -0.6264538 0.3295078 0.5757814 -0.62124058 1 
#2: 0.1836433 -0.8204684 -0.3053884 -2.21469989 1 
#3: -0.8356286 0.4874291 1.5117812 1.12493092 2 
#4: 1.5952808 0.7383247 0.3898432 -0.04493361 2 

#DT2 
#   V1  V2  V3   V4 id 
#1: -0.01619026 0.8212212 0.9189774 0.07456498 1 
#2: 0.94383621 0.5939013 0.7821363 -1.98935170 2 

cols <- grep(colnames(DT2), pattern='V.*', value=T)                                         
ids <- DT2[,unique(id)]                                                
for (id_i in ids) {                                                 
    l <- as.matrix(DT[id==id_i,(cols),with=F])                                          
    r <- diag(t(DT2[id==id_i,(cols),with=F])[,1L])                                         
    DT[id==id_i,(cols):=as.data.table(l%*%r)]                                            
}                                                     


    #DT(i,j) = DT(i,j)*DT2(j) with id matching 
      V1   V2   V3   V4 id 
1: 0.010142452 0.2705988 0.5291300 -0.04632279 1 
2: -0.002973234 -0.6737860 -0.2806450 -0.16513906 1 
3: -0.788696543 0.2894848 1.1824189 -2.23788323 2 
4: 1.505683787 0.4384920 0.3049105 0.08938875 2 

必须有办法做到这一点有效地利用by.EACHI但解决的办法是躲避我

+0

如果'DT [,(cols):= as.data.table(l%*%r)]'是DT [id_i,(cols):= as.data.table(l%*%r) ]'? – lmo

+0

@lmo是的,你完全正确 – statquant

+7

如何使用矩阵的matricial产品? –

回答

0

下面是使用sapply的解决方案。

ids <- unique(c(DT$id,DT2$id)) 
nc <- ncol(DT) 
myprod <- function(k) { 
    mtx1 <- as.matrix(DT[id==k][,-nc,with=F]) 
    nr <- nrow(mtx1) 
    mtx2 <- t(matrix(rep(as.matrix(DT2[id==k][,-nc,with=F]),nr),ncol=nr)) 
    mtx1*mtx2 
} 
do.call(rbind,sapply(ids, myprod,simplify =F)) 

# Results 
       V1   V2   V3   V4 
[1,] 0.010142452 0.2705988 0.5291300 -0.04632279 
[2,] -0.002973234 -0.6737860 -0.2806450 -0.16513906 
[3,] -0.788696543 0.2894848 1.1824189 -2.23788323 
[4,] 1.505683787 0.4384920 0.3049105 0.08938875 
+0

你似乎没有得到正确的答案 – statquant

+0

我根据你对问题的描述改变了我的答案。 –

1

我不知道,这是一个显着改善,从你所拥有的,但它确实使用联接和EACHI ...

DT[DT2, on="id", by=.EACHI, 
    {temp=tcrossprod(matrix(c(x.V1, x.V2, x.V3, x.V4), ncol=4), 
        diag(c(i.V1, i.V2, i.V3, i.V4))) 
    as.data.table(temp)}] 
    id   V1   V2   V3   V4 
1: 1 0.010142452 0.2705988 0.5291300 -0.04632279 
2: 1 -0.002973234 -0.6737860 -0.2806450 -0.16513906 
3: 2 -0.788696543 0.2894848 1.1824189 -2.23788323 
4: 2 1.505683787 0.4384920 0.3049105 0.08938875 

我摆弄试图自动化的建设x.V1 ...和i.V1变量名称,但未成功。