查找数组中的一个或多个数字是否可以等于某个数字

时间:2018-08-17 08:26:09

标签: javascript algorithm loops

比方说,我有一个像9这样的设定数字,并且有一个包含#s [1,2,4,6,3,9]的数组。我想知道哪种循环方法是最好的方法,看看其中一个或多个#加起来是否等于9。我最初的想法是:

  • 检查当前数组索引值是否等于 magicNum
  • 如果当前数字小于magicNum,则将其与数组中的另一个数字加在一起,并不断循环查看它是否匹配
  • 如果上述方法无效,请移至下一个数字并重复。

我的第一张支票还可以,但是这是我遇到的其他两张支票。对于初学者来说,我知道除使用reduce之外,可能(或可能不需要)递归函数。算法还不是我的强项(但是),但是我渴望并且更愿意改进。任何类型的指导将不胜感激。

const magicNum = 9;

const arr = [10,1,2,4,6,3];

for (let i = 0, arrLength = arr.length; i < arrLength; i++) {
  if (arr[i] === magicNum) {
    console.log('Number Found!');
    continue;
  } else if (arr[i] > magicNum) {
    continue;
  } else if (arr[i] < magicNum) {
    // Stuck here
  }
}

2 个答案:

答案 0 :(得分:1)

您可以采用迭代和递归的方法来查找子集总和。

function getSubsets(array, sum) {

    function fork(i = 0, s = 0, t = []) {
        if (s === sum) {
            result.push(t);
            return;
        }
        if (i === array.length) {
            return;
        }
        if (s + array[i] <= sum) { // shout circuit for positive numbers only
            fork(i + 1, s + array[i], t.concat(array[i]));
        }
        fork(i + 1, s, t);
    }

    var result = [];
    fork();
    return result;
}

console.log(getSubsets([10, 1, 2, 4, 6, 3], 9));
.as-console-wrapper { max-height: 100% !important; top: 0; }

要仅获取第一个子集,可以使用找到的第一个值数组退出递归。

function getFirstSubset(array, sum) {

    function fork(i = 0, s = 0, t = []) {
        if (s === sum) {
            return  t;
        }
        if (i === array.length) {
            return;
        }
        return fork(i + 1, s + array[i], t.concat(array[i]))
            || fork(i + 1, s, t);
    }

    return fork();
}

console.log(getFirstSubset([10, 1, 2, 4, 6, 3], 9));
.as-console-wrapper { max-height: 100% !important; top: 0; }

答案 1 :(得分:0)

这更多是一个动态编程问题。 您可以参考以下内容实现此目的: https://www.geeksforgeeks.org/perfect-sum-problem-print-subsets-given-sum/

您真正需要的是列出数字总和等于给定幻数的数组的所有子集。

编辑: find all subsets that sum to a particular value

的副本

从以上帖子中发布@Redu的答案:

function getSummingItems(a,t){
  return a.reduce((h,n) => Object.keys(h)
                                 .reduceRight((m,k) => +k+n <= t ? (m[+k+n] = m[+k+n] ? m[+k+n].concat(m[k].map(sa => sa.concat(n)))
                                                                                      : m[k].map(sa => sa.concat(n)),m)
                                                                 :  m, h), {0:[[]]})[t];
}
var arr = Array(20).fill().map((_,i) => i+1), // [1,2,..,20]
    tgt = 9,
    res = [];

console.time("test");
res = getSummingItems(arr,tgt);
console.timeEnd("test");
console.log("found",res.length,"subsequences summing to",tgt);
console.log(JSON.stringify(res));