找到两个将等于所需总和的数字

时间:2018-08-17 15:44:42

标签: javascript

我进行了一次技术面试,问题之一是在数组中找到两个等于所需总和的数字。对于我的一生,我找不到解决方法。

var input = [3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5];
var dSum = 28; // return would be [12,16]

11 个答案:

答案 0 :(得分:8)

使用Set()来解决O(n)中的此问题。方法很简单:

  • 采取一个空集。并针对input中的每个元素e:

    (a)如果该集合包含sum - e。如果是,则打印(e, sum -e)对。

    (b)将e插入到集合中。

    尝试以下操作:

let input = [3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5];
let dSum = 28;
let set = new Set();

for(item of input) {
  let num = dSum - item;
  if(set.has(num)) {
    console.log(num + " " + item);
    break;
  }
  set.add(item);
}

答案 1 :(得分:3)

请查看以下简单代码,因为我很确定这就是您所需要的:

function detectPair(sum, array) {
  for (i=0; i<array.length; i++) {
    for (j=0; j<array.length; j++) {
      if (i == j) continue;
      else if (array[i] + array[j] === sum) return [array[i], array[j]];
    }
  }; return null;
}


let sum = 28;
let array = [3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5]

console.log(detectPair(sum, array)); //return would be [12,16]


编辑@ uom-pgregorio :“ There wasn't any constraints that the same number can't be used. So a 14 + 14 in this case should still be accepted

我很确定您已经混淆了一些东西if (i == j) continue;行并不能防止14+14是正确的情况,它可以防止数组仅包含一个数字(like 14),它多次使用相同的数字。

==> `i == j` is checking the indexes not the values

也许只是尝试此设置

let sum = 28;
let array = [3, 5, 7, 14, 14] // includes 14 two times

答案 2 :(得分:2)

function findSumPair(input, target) {
   for(let a = 0; a < input.length; a++) {
      for(let b = a; b < input.length; b++) {
         if(input[a]+input[b] === target)
            return [input[a], input[b]];
      }
   }
}
console.log(findSumPair([3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5], 28));

内部循环可以从外部循环的当前索引(而不是0)开始,因为已经检查了先前的组合。

答案 3 :(得分:1)

var input = [3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5];
var dSum = 28; // return would be [12,16]

let el1 = Math.max(...input)
let el2 = Math.max(...input.filter(i => i !== el1))

console.log([el1, el2])

let input = [3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5];
let dSum = 28; // return would be [12,16]
let result

for (let i = 0; i < input.length; i++)
  for (let k = i; k < input.length; k++)
    if (i !== k && input[i] + input[k] === dSum)
      result = [input[i], input[k]]

console.log(result)

答案 4 :(得分:1)

除了双嵌套解决方案和具有多个循环的解决方案之外,您还可以使用带有哈希表的单循环方法来处理仍缺少的数字,如果在数组中找到该数字,则可以短路。

这种方法是一种快速的方法,因为它使用一个for循环,其中一个对象作为快速访问的存储,而一个变量value用于array[i]

大O在最坏的情况下是O(n)。

function getPair(array, sum) {
    var i, l,
        hash = Object.create(null),
        value;
        
    for (i = 0, l = array.length; i < l; i++) {
        value = array[i];
        if (hash[value]) {
            return [sum - value, value];
        }
        hash[sum - value] = true;
    }
}

console.log(getPair([3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5], 28));

答案 5 :(得分:0)

我想说这行得通,但是算法确实很糟糕,我想是O(n ^ 2)。

for (i of input) {
    for (j of input) {
        if (i + j == dSum)
            console.log([i, j]);
    }
}

答案 6 :(得分:0)

function findPair(input, sum) {
  for(let i = 0; i < input.length; i++) {
    for(let j = i; j < input.length; j++) {
      if(input[i] + input[j] == sum) return [input[i], input[j]];
    }
  }
  return [];
}

console.log(findPair([3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5], 28));

答案 7 :(得分:0)

尝试以下操作:

   for (var i = 0; i < input.length; i++)
    for (var j = 0; J < input.length; j++)
        if (input[i]+input[j] == dSum)
            console.log([input[i], input[j]])

编辑: 我认为存在i <> j的约束。我删除了约束

答案 8 :(得分:0)

var input = [3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5];
var dSum = 28;
twoSum(input, dSum);
function twoSum (arr, target) {
  let results = [];
  for (let i=0; i<arr.length; i++) {
    for (let j=i+1; j<arr.length; j++) {
      if (arr[j] === target - arr[i]) {
        results.push([arr[i], arr[j]])
      }
    }
  }
  return results;
}

答案 9 :(得分:0)

@amrender-singh在这里是最好的答案。

为了荣誉,这是一个片段,使用他的代码在Array

中查找具有特定值的第一个或所有和

const log = (...strs) => 
  document.querySelector("pre").textContent += `${strs.join(" ")}\n`;
const array = [3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5];

log("All possible sums 28 in array:", findSumsInArray(array, 28));
log("First sum 28 in array:", findSumsInArray(array, 28, true));
log("All possible sums 22 in array:", findSumsInArray(array, 22));
log("First sum 22 in array:", findSumsInArray(array, 22, true));
log("All possible sums 12 in array:", findSumsInArray(array, 12));
log("First sum 12 in array:", findSumsInArray(array, 12, true));
log("First sum 28 in array [3, 5, 7, 14, 14]:", 
     findSumsInArray([3, 5, 7, 14, 14], 28, true));

function findSumsInArray(array, sum2Find, firstOnly) {
  let set = new Set(array);
  let result = [];
  const errorStr = `Sum ${sum2Find} not possible in [${array}]`;
  for (let item of array) {
    let num = sum2Find - item;
    if (set.has(num)) {
      const report = `${num}+${item}`;
      if (firstOnly) {
        return report;
      }
      result.push(report);
      set.delete(item);
   }
  }
  return result.length ? `[${result.join(", ")}]` : errorStr;
}
<pre></pre>

答案 10 :(得分:0)

我的贡献有点晚了,但是似乎没有人发布过强制性的JavaScript单行代码。

let input = [3, 5, 7, 9, 4, 8, 5, 12, 4, 9, 16, 5];
let dSum = 28;
let Result = [];

input.forEach( i=>{ input.forEach( j=>{ i+j==dSum && Result.push([i,j]); }); });

Result数组将包含解决方案,在这种情况下,有两个解决方案:

[[12, 16], [16, 12]]

将其概括为一个函数,其中代表inputdSum的值是用户定义的参数:

pairsFromArrayWithSum = (total, Numbers) 
                      => Numbers.forEach(a => { 
                         Numbers.forEach(b => { 
                         a + b == total && Result.push([a,b]);
                         }); });

然后,给出:

Result = [];
pairsFromArrayWithSum(50, [2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47]);

Result数组将包含:

[ [ 3, 47 ],
  [ 7, 43 ],
  [ 13, 37 ],
  [ 19, 31 ],
  [ 31, 19 ],
  [ 37, 13 ],
  [ 43, 7 ],
  [ 47, 3 ] ]