【问题标题】:Multi-dimensional Array; JavaScript; Algorithum多维数组; JavaScript;算法
【发布时间】:2021-08-30 22:47:42
【问题描述】:

详情
我正在研究处理多维数组的算法。如果有一个零,那么同一列的元素,但后面的数组也将为零。我希望能够对未归零的项目求和。

Example:

matrix = [[0, 1, 1, 2],
          [0, 5, 0, 0], 
          [2, 0, 3, 3]] --->2, 3, and 3 will not be counted since there is a zero above it.

the output should be: 1+1+2+5 = 9

我目前的工作

function matrixElementsSum(matrix) {
    var sum = 0;
    for(var i=0;i<matrix.length;i++){
    console.log(matrix[i])
        for(var j=0;j<=matrix.length;j++){
            console.log(matrix[i][j])
            if(matrix[i][j] == 0){
                console.log(true)
//------------>Here is my problem
            }
            else {
                console.log(false)
            }
            if(matrix[i][j] !== 0){
                sum+=matrix[i][j];
            }
        }
    }
    return sum;
}

我想用这个:

matrix[i+1][j] = 0;

但我收到此错误:

TypeError: Cannot read property '1' of undefined

有人可以帮助我理解为什么我的思考过程不起作用以及任何继续的建议吗?

谢谢!

【问题讨论】:

  • 你是怎么想到1+1+2+5 = 9的。你会编辑答案并解释它吗?我的意思是你的预期结果是什么?如何?
  • j&lt;=matrix.length 没有意义。你的意思是j &lt; matrix[i].length
  • 遍历数组索引时,条件应该是index &lt; array.length,而不是index &lt;= array.length
  • 当你在最后一行时,你不能做matrix[i+1][j] = 0;。所以在做之前检查i == matrix.length - 1
  • @decpk 好的,我编辑了。

标签: javascript algorithm matrix multidimensional-array


【解决方案1】:

如果您不想在算法期间修改矩阵,那么一种解决方案是为每一列设置标志,指​​示您是否已经在该列中遇到了 0:

function matrixElementsSum(matrix) {
    let sum = 0;
    let flags = Array(matrix[0].length).fill(true);
    for (let row of matrix) {
        for (let j = 0; j < flags.length; j++) {
            if (flags[j] &&= row[j]) sum += row[j];
        }
    }
    return sum;
}

let matrix = [[0, 1, 1, 2], 
              [0, 5, 0, 0], 
              [2, 0, 3, 3]];
console.log(matrixElementsSum(matrix));

请注意,j 上的循环应具有 j &lt; matrix[0].length 条件

如果您的 IDE 抱怨 if 条件中的分配,那么您可以选择从条件中拆分分配:

flags[j] &&= row[j];
if (flags[j]) sum += row[j];

或者,如果您不支持此运算符:

flags[j] = flags[j] && row[j];
if (flags[j]) sum += row[j];

【讨论】:

  • 当我在我的 VS Code 中运行它时,它不喜欢 if 语句?
  • 可能是因为它想警告表达式发生的赋值,但它是在这里的。您可以选择先做作业,然后根据需要进行评估。
  • 好的,我的 VS 代码中还有其他设置。我改变了它并重试了你最初的方法,它有效,但答案是 7 而不是 9!
  • 那么你有一些不同的东西。您可以在我的答案中运行 sn-p 并查看它的输出 9
  • 宾果游戏!最后的编辑成功了!所以我不支持运营商。我不确定我是否完全理解,但现在我已经完成了这项工作,我将能够将其分解。谢谢!
【解决方案2】:

试试这个代码

const mat1 = [[0, 1, 1, 2], [0, 5, 0, 0], [2, 0, 3, 3]]
    
function matrixElementsSum(matrix) {

  for (let i = 0; i < matrix.length; i++) {
      const row = matrix[i]
      for (let j = 0; j < row.length; j++) {
          if (matrix[i][j] === 0) {
              for (let k = i; k < matrix.length; k++) {
                  matrix[k][j] = 0
              }
          }
      }
  }

  let total = 0
  for (let i of matrix)
      for (let j of i)
          total += j;

  return total;
}

console.log(matrixElementsSum(mat1));

【讨论】:

【解决方案3】:

使用 Javascript 处理矩阵中的行通常比处理列容易得多。因此,一种简洁的编写方法是首先转置矩阵(将其翻转到西北-东南对角线),然后对每一行求和,直到达到零,最后对这些结果求和。

[
  [ 0, 0, 5 ], // => 0     = 0
  [ 1, 5, 0 ], // => 1 + 5 = 6
  [ 1, 0, 3 ], // => 1     = 1
  [ 2, 0, 3 ], // => 2     = 2
]              //          +__
//                           9

transposesum 函数非常容易(并且很可能存储在个人实用程序库中,因为它们很可能会被重复使用。

我们还需要一个sumToFirstZero 函数。在这里,我们编写了一个递归的方法,它设法隐藏了一点复杂性,因为n ? 与我们的两个基本情况的其他所有情况不同——当我们完成了行并且因此nundefined,并且当n 为零时.在任何一种情况下,我们都简单地返回0。在其他情况下,我们将当前值添加到对数组其余部分的递归调用中。

主函数只是将这三个放在一起。

const transpose = (xs) => 
  xs [0] .map ((_, i) => xs .map (r => r[i]))
  
const sum = (ns) =>
  ns .reduce ((a, b) => a + b, 0)

const sumToFirstZero = ([n, ...ns]) => 
  n ? n + sumToFirstZero (ns) : 0

const problem = (matrix) =>
  sum (transpose (matrix) .map (sumToFirstZero))

console .log (problem ([
  [0, 1, 1, 2], 
  [0, 5, 0, 0], 
  [2, 0, 3, 3]
]))

为了说明sumToFirstZero 是如何设法隐藏一点复杂性的,这将是同一功能的逻辑更清晰的版本:

const sumToFirstZero = ([n, ...ns]) => 
  n == undefined 
    ? 0
  : n == 0
    ? 0
  : n + sumToFirstZero (ns)

但是由于n 必须是一个数字或undefined,如果我们在递归中触底,我们可以通过(! n) ? 0 : n + sumToFirstZero (ns) 来利用JS 的布尔强制,或者,就像我们在上面使用n ? n + sumToFirstZero (ns) : 0 所做的那样

当然,我们必须对(转置的)行执行此操作。我们可以直接在列上工作,摆弄数组参数。但我发现这要简单得多。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-05-24
    • 2022-01-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-04-06
    • 2023-04-01
    • 1970-01-01
    相关资源
    最近更新 更多