在JavaScript中找到最大的子数组长度

时间:2018-08-30 13:59:48

标签: javascript arrays

我做了一个寻找最大子阵列长度的函数。它工作正常,但在某些输入下无法显示正确的输出。

这是我的代码:

    function maxLength(a, k) {
      function sumOfArray(arr) {
        return arr.reduce((a, b) => a + b, 0);
      }

      var sub_array = [];
      for (var i = 0; i < a.length; i++) {
        for (var j = i + 1; j < a.length; j++) {
          if (j - i > sub_array.length && sumOfArray(a.slice(i, j)) < k) {
            sub_array = a.slice(i, j);
          }
        }
      }
      return sub_array.length;
    }


console.log(maxLength([3,1,2,1,4], 4))

显示错误答案的输入为:[3,1,2,1,4]和k = 4,其输出为2,但正确答案为3

如何修复代码

任何帮助将不胜感激

4 个答案:

答案 0 :(得分:1)

如果我没记错,您正在尝试使用最大长度为sum的子数组作为input(k)。

对于您的if condition => < k < =k

的更改
if (j - i > sub_array.length && sumOfArray(a.slice(i, j)) < k) 

if (j - i > sub_array.length && sumOfArray(a.slice(i, j)) <= k)  

function maxLength(a, k) {
  function sumOfArray(arr) {
    return arr.reduce((a, b) => a + b, 0);
  }

  var sub_array = [];
  for (var i = 0; i < a.length; i++) {
    for (var j = i + 1; j < a.length; j++) {
      if (j - i > sub_array.length && sumOfArray(a.slice(i, j)) <= k) {
        sub_array = a.slice(i, j);
      }
    }
  }
  return sub_array.length;
}
console.log(maxLength([3,1,2,1,4],4));
console.log(maxLength([3,1,2,1,4],7));
console.log(maxLength([1,1,1,1,3,1,2,1,4],7));

答案 1 :(得分:0)

@NullPointer进行了简单的修改,似乎可以使您的函数正常工作。我认为这是简化问题的另一种方法:

const sum = (xs) => xs.reduce((a, b) => a + b, 0)
const range = (lo, hi) => [...new Array(hi - lo + 1)].map((_, i) => i + lo);

const subarrays = (arr) => arr
  .map((x, i) => range(i + 1, arr.length + 1).map(j => arr.slice(i, j)))  
  .reduce((a, b) => a.concat(b), [[]])

const maxLength = (arr, limit) => Math.max.apply(null,
  subarrays(arr)
    .filter(xs => sum(xs) <= limit)
    .map(xs => xs.length)
)

console.log(maxLength([3, 1, 2, 1, 4], 4))

  • sum给出数组中值的总和。
  • range创建一个介于lohigh之间的数字数组
  • subarrays列出了数组的子数组。例如subarrays([2, 3, 5]) 返回[[], [2], [2, 3], [2, 3, 5], [3], [3, 5], [5]]

当然

  • maxLength是您要编写的函数。

这种方法肯定会失去潜在的效率,这涉及到不必测试扩展​​超出限制的子阵列。但是这些效率也没有用在原始文件中。

sumrange显然是可重用的函数,并且subarrays也可能派上用场。

答案 2 :(得分:0)

在对不同的情况进行测试之后,我最终发现应该更改部分代码。

第一个for循环必须i <= a.length,第二个for循环j <= a.length

if语句sumOfArray(a.slice(i, j)) < k中也应更改为:

sumOfArray(a.slice(i, j)) <= k

这些更改显示了所有情况下的正确答案。

下面是代码:

function maxLength(a, k) {
function sumOfArray(arr) {
  return arr.reduce((a, b) => a + b, 0);
}

var sub_array = [];
for (var i = 0; i <= a.length; i++) {
  for (var j = i + 1; j <= a.length; j++) {
    if (j - i > sub_array.length && sumOfArray(a.slice(i, j)) <= k) {
      sub_array = a.slice(i, j);
    }
  }
} 
return sub_array.length;

}

答案 3 :(得分:0)

上述问题:

  • 不是防御性的(我也可以检查代码中的类型)
  • 从最小的块开始,先进行最大的跨度,以便您尽早终止

尝试:

function maxLength(a, k) {
  if(!a || !k) return 0
  for(let scanlen = a.length; scanlen; scanlen--){
    for(let start = 0; start+scanlen<=a.length; start++){
      if( a.slice(start, start+scanlen).reduce((acc,curr)=> acc+curr ) <= k)
         return scanlen
    }
  }
  return 0
}