【问题标题】:R Combining MatricesR 组合矩阵
【发布时间】:2025-12-12 07:55:01
【问题描述】:

我有两个矩阵,一个是二进制(零或一),另一个是相同维度的整数矩阵,这些是方阵。

我想要一种以特定方式组合它们的有效方法,而无需沿每个元素进行迭代。

我想组合它们的方式是从矩阵 A 和矩阵 B 得到一个结果矩阵,对于元素,它采用非零的最小数字。

谁能想到 R 中的一个技巧来实现这一点,我已经尝试在数学上做到这一点,但一直不够,我想知道是否有办法用条件语句覆盖矩阵?

【问题讨论】:

  • 如果 A 和 B 都为 0 会怎样?
  • 我认为您欠我们一个具有预期输出的示例。
  • @flodel Dwin 的解决方案是我的目标。在所述解决方案中在 matC[1,3] 处看到的 0,0 实例将是错误的结果,但理论上不应发生。我想给你一个更全面的例子,但是当我本周正在整理它背后的理论时,这个过程在我的脑海中还不足以做到这一点。我很乐意在一周左右的时间内跟进。从广义上讲,这将是用于构建基因交互网络的东西。
  • ...但是matC[1,3] 不是(0, 0) 实例,它是(0, 1) 实例。所以我预计结果是1

标签: r math matrix


【解决方案1】:
 matA <- matrix(-8:7, 4,4); set.seed(123)
 matB <- matrix(sample(0:1, 16, repl=TRUE), 4, 4)
 matC <- matrix(NA, nrow(matA), ncol(matA))
 matC[] <- pmin( matA, MatB)
 matC[ matB==0] <- matA[matB==0]

 matB
#-----------
     [,1] [,2] [,3] [,4]
[1,]    0    1    1    1
[2,]    1    0    0    1
[3,]    0    1    1    0
[4,]    1    1    0    1
 matC
#---------
     [,1] [,2] [,3] [,4]
[1,]   -8   -4    0    1
[2,]   -7   -3    1    1
[3,]   -6   -2    1    6
[4,]   -5   -1    3    1

flodel 的方法产生:

> ifelse(matB == 0, matB, pmin(matA, matB))
     [,1] [,2] [,3] [,4]
[1,]    0   -4    0    1
[2,]   -7    0    0    1
[3,]    0   -2    1    0
[4,]   -5   -1    0    1

mnel 的方法产生:

> (matB * !matA) + matA
     [,1] [,2] [,3] [,4]
[1,]   -8   -4    1    4
[2,]   -7   -3    1    5
[3,]   -6   -2    2    6
[4,]   -5   -1    3    7

【讨论】:

  • 感谢您的解决方案,但不幸的是,虽然这正是我打算在较小的数据集上做的事情,但当我将其扩展到大型数据集时,我长矢量错误:(
  • matA 和 matB 都是 0,所以真的没有其他选择了。
  • 不,如果我运行你的代码 matA[1, 3]0matB[1, 3]1,但 matC[1, 3]0
  • 嗯。我不在带有 R 的机器上,但我的湿件执行符合您的逻辑。也许 [] 中的条件应该是matA==0|matB==0。未经测试。
【解决方案2】:

我的猜测是:

ifelse(A == 0, B, pmin(A, B))

或许

ifelse(A == 0, B, ifelse(B == 0, A, pmin(A, B)))

如果这不是您要查找的内容,请澄清(并可能提供示例。)

【讨论】:

    【解决方案3】:

    从@A_Skeleton 对缩放的评论中,您可以将矩阵分成块:

    mnel <- function(matA, matB) {
      (matB * !matA) + matA
    }
    
    # method takes a function as the argument
    mcombine <- function(matA, matB, method) {
      chunkSize <- 10000
      matC <- matrix(0, nrow(matA), ncol(matA))
      for (i in 1:floor(nrow(matA) / chunkSize)) {
        curRange <- (chunkSize * (i-1) + 1):(i * chunkSize)
        matC[curRange,] <- method(matA[curRange,], matB[curRange,])
      }
      # handle case where dimensions don't divide exactly into chunks
      lastRange <- i*chunkSize:nrow(matA)
      matC[lastRange,] <- method(matA[lastRange,], matB[lastRange,])
      matC
    }
    
    # Using mnel's method:
    matC <- mcombine(matA, matB, mnel)
    

    【讨论】: