我有两个距离矩阵..但是它们中的任何一个都可能缺少项目,并且它们可能乱序 - 例如:
矩阵 #1(缺少 c 项)
a b d
a 0 2 3
b 2 0 4
d 3 4 0
矩阵 #2(缺少项目 b,且项目顺序困惑)
d c a
d 0 1 2
c 1 0 1
a 2 1 0
我想找出矩阵之间的差异,同时假设任何缺失的项均为 0。因此,我得到的矩阵应该是:
a b c d
a 0 2 1 1
b 2 0 0 4
c 1 0 0 1
d 1 4 1 0
解决这个问题的最佳方法是什么?我应该对两个矩阵进行排序,然后填充缺失的列/行,以便我可以直接使用abs(m1-m2),还是有一种方法可以使用行/列标题让它们在减法时自动“匹配”?
这些矩阵的大小约为 5000x5000 左右,我将有大约 1000 个矩阵进行成对比较,因此,如果这将使每次计算速度显着加快,我宁愿对数据进行预处理。
欢迎任何提示或建议。我通常是一名非 R 程序员,因此我通常会提出的迭代解决方案将永远花费很长时间——我希望“R 方式”做事的速度会明显更快。
最佳答案
我们创建一个名称索引('Un1'),即 union
第一个 ('m1') 和第二个 ('m2') 的名称 matrix
。通过指定基于“Un1”的维度和暗淡名称来创建两个新的 0 矩阵(“m1N”、“m2N”)。通过行/列索引,我们将这些矩阵中的 0 值更改为 'm1'、'm2' 中的值,相减并得到绝对值。
Un1 <- sort(union(colnames(m1), colnames(m2)))
m1N <- matrix(0, ncol=length(Un1), nrow=length(Un1), dimnames=list(Un1, Un1))
m2N <- m1N
m1N[rownames(m1), colnames(m1)] <- m1
m2N[rownames(m2), colnames(m2)] <- m2
abs(m1N-m2N)
# a b c d
#a 0 2 1 1
#b 2 0 0 4
#c 1 0 0 1
#d 1 4 1 0
更新
如果我们有几个带有对象名称的矩阵 m
后面跟着数字,我们可以将它们放在 list
中。我们使用 ls
获取对象名称以及 list
中的值与 mget
。循环遍历list
与 lapply
要获取列名称,请使用 union
如f
在Reduce
, sort
获取 unique
元素。
lst <- mget(ls(pattern='m\\d+')) #change the pattern accordingly
Un1 <- sort(Reduce(union, lapply(lst, colnames)))
我们可以创建另一个 list
与 matrix
0。
lst1 <- lapply(seq_along(lst), function(i)
matrix(0, ncol=length(Un1), nrow=length(Un1), dimnames=list(Un1, Un1)))
我们可以使用“lst”相应矩阵的行/列索引(使用 Map
来更改“lst1”的相应元素) .
lst2 <- Map(function(x,y) {x[rownames(y), colnames(y)] <- y; x}, lst1, lst)
如果我们需要成对差异,combn
可能是一个选择
lst3 <- combn(seq_along(lst2),2, FUN=function(x)
list(abs(lst2[[x[1]]]-lst2[[x[2]]])))
names(lst3) <- combn(seq_along(lst2), 2, FUN=paste, collapse='_')
关于r - 填充R中距离矩阵中缺失的行/列,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32576538/