R:根据行名和列名添加矩阵

时间:2014-09-25 15:45:12

标签: r matrix addition

我有两个矩阵,我想根据它们的行名和列名求和。矩阵不一定具有所有行和列 - 一些矩阵中可能缺少某些行。

例如,考虑两个矩阵A和B:

A=                 B=
  a b c d            a c d e
v 1 1 1 0          v 0 0 0 1
w 1 1 0 1          w 0 0 1 0
x 1 0 1 1          y 0 1 0 0
y 0 1 1 1          z 1 0 0 0

矩阵A中缺少列e,矩阵B中缺少列B. 矩阵A中缺少行z,矩阵B中缺少行x。

我要找的总和表是:

Sum=
  a b  c d e
v 1 1  1 0 1
w 1 1  0 2 0
x 1 0  1 1 na
y 0 1  2 1 0
z 1 na 0 0 0

只要矩阵完整,即具有所有数据,最终矩阵中的行和列排序就不重要了。缺失的价值观不一定是" Na",但可能是" 0"代替。

我不确定是否有办法做到这一点并不涉及循环。任何帮助将不胜感激。

我的解决方案

我设法通过将矩阵转换为数据帧,按行绑定数据帧然后将结果数据帧转换回矩阵来轻松完成此操作。这看起来很有效,但也许有人可以仔细检查或让我知道是否有更好的方法。

library(reshape2)
A_df=as.data.frame(as.table(A))
B_df=as.data.frame(as.table(B))

merged_df=rbind(A_df,B_df)

Summed_matrix=acast(merged_df, Var1 ~ Var2, sum)

merged_df看起来像这样:

   Var1 Var2 Freq
1     v    a    1
2     w    a    1
3     x    a    1
4     y    a    0
5     v    b    1
6     w    b    1
etc...

1 个答案:

答案 0 :(得分:3)

可能你可以试试:

cAB <- union(colnames(A), colnames(B))
rAB <- union(rownames(A), rownames(B))

A1 <- matrix(0, ncol=length(cAB), nrow=length(rAB), dimnames=list(rAB, cAB))
B1 <- A1

indxA <- outer(rAB, cAB, FUN=paste) %in% outer(rownames(A), colnames(A), FUN=paste) 
indxB <- outer(rAB, cAB, FUN=paste) %in% outer(rownames(B), colnames(B), FUN=paste)
A1[indxA] <- A
B1[indxB] <- B

A1+B1 #because it was mentioned to have `0` as missing values
#  a b c d e
#v 1 1 1 0 1
#w 1 1 0 2 0
#x 1 0 1 1 0
#y 0 1 2 1 0
#z 1 0 0 0 0

如果您想将NA作为缺失值

A1 <- matrix(NA, ncol=length(cAB), nrow=length(rAB), dimnames=list(rAB, cAB))
B1 <- A1

A1[indxA] <- A
B1[indxB] <- B

indxNA <- is.na(A1) & is.na(B1)
A1[is.na(A1)!= indxNA] <- 0
B1[is.na(B1)!= indxNA] <- 0


A1+B1
#  a  b c d  e
#v 1  1 1 0  1
#w 1  1 0 2  0
#x 1  0 1 1 NA
#y 0  1 2 1  0
#z 1 NA 0 0  0

或使用reshape2

library(reshape2)
acast(rbind(melt(A), melt(B)), Var1~Var2, sum) #Inspired from the OP's idea
#  a b c d e
#v 1 1 1 0 1
#w 1 1 0 2 0
#x 1 0 1 1 0
#y 0 1 2 1 0
#z 1 0 0 0 0

数据

A <- structure(c(1L, 1L, 1L, 0L, 1L, 1L, 0L, 1L, 1L, 0L, 1L, 1L, 0L, 
1L, 1L, 1L), .Dim = c(4L, 4L), .Dimnames = list(c("v", "w", "x", 
"y"), c("a", "b", "c", "d")))

B <- structure(c(0L, 0L, 0L, 1L, 0L, 0L, 1L, 0L, 0L, 1L, 0L, 0L, 1L, 
0L, 0L, 0L), .Dim = c(4L, 4L), .Dimnames = list(c("v", "w", "y", 
"z"), c("a", "c", "d", "e")))
相关问题