【问题标题】:create a function that accepts an integer and generates an array containing pairs of integers [a, b] sorted by increasing values of a and then b创建一个函数,该函数接受一个整数并生成一个数组,其中包含整数对 [a, b] 按递增的 a 和 b 的值排序
【发布时间】:2020-08-26 09:21:14
【问题描述】:

我在我的软件工程训练营中遇到了这个练习问题,希望有人能指出我正确的方向。

编写一个函数 generatePairs,它接受一个整数并生成一个包含整数对 [a, b] 的数组。这些对应该通过增加 a 的值然后增加 b 的值来排序。 以下是不同输入应返回的一些示例:

generatePairs(3) // [ [0, 0], [0, 1], [0, 2], [0, 3], [1, 1], [1, 2], [1, 3], [2, 2], [2, 3], [3, 3] ]
generatePairs(2) // [ [0, 0], [0, 1], [0, 2], [1, 1], [1, 2], [2, 2] ]
generatePairs(1) // [ [0, 0], [0, 1], [1,1]]
generatePairs(0) // [ [0, 0]]

到目前为止,这是我的代码:

function generatePairs (num){
  array = [];
  // 0 [0,0] [0,1]

  // 1

  // 2
  for (i = 0; i<=num; i++){
    array.push([i,i]);
    if ((i+1)<=num) {
        array.push([i,i+1])
    }

    if ( num - i <= num && i===0 && num < i ) {
      array.push([i,num])
      if (num + i < i) {
        array.pop();
      }
    }

  } 
  return array;
}

generatePairs(2) // [ [0, 0], [0, 1], [0, 2], [1, 1], [1, 2], [2, 2] ]

我遇到的问题是,例如,当我尝试使用 2 时,我缺少 [0,2] 子数组。我尝试解决此问题的方法主要包括额外的 if 和 else 循环,但是对于我尝试过的每一个循环,我要么最终得到比它们应该更高的子数组,要么是一个半工作系统这仅适用于 2 而不适用于可以输入到函数中的任何数字。

【问题讨论】:

  • 嘿!现在查看您的代码,但以供将来参考,请在定义变量时使用var/let,以避免将来进行大量错误搜索。
  • 改变了我对忍者代码的回答;)

标签: javascript arrays for-loop if-statement sub-array


【解决方案1】:

是不是比这简单多了?

function generatePairs(num) {
  let arr = []
  for (let i = 0; i <= num; i++) {
    for (let j = i; j <= num; j++) {
      arr.push([i, j])
    }
  }
  return arr
}
console.log(generatePairs(2));

【讨论】:

  • 3 { 和只有 2 } ,以及糟糕的第二个循环......你的代码是错误的
  • 是的,我的 Firefox 在打字时崩溃了,所以我用手机写了。需要再次在笔记本电脑上编辑一次。
  • 大声笑,编辑后意识到这是多么错误哈哈。再也不用手机打字了。
【解决方案2】:

解决方案:(忍者代码)

const generatePairs = n => Array.apply(null,{length:((n+1)*(n+2)/2)}).reduceRight((a,c,i)=>{
  a.r.push([...a.p])
  if(++a.p[1]>n) a.p[1]=++a.p[0]
  return i?a:a.r
},{p:[0,0],r:[]})

for (let x=4;x--;) document.write(x,'->',JSON.stringify(generatePairs(x)), '<br>')

【讨论】:

    【解决方案3】:

    这就是你想要的。您循环遍历第一部分的 num 直到到达 num 并且每个第一部分从第一部分循环到 num。

    function generatePairs(num) {
        var output = []
    
        for (var i = 0; i < num + 1; i++) {
           for (var k = i; k < num + 1; k++) {
              output.push([i, k])
           }
        }
    
        return output
    }
    

    【讨论】:

      【解决方案4】:

      递归

      我们可以一厢情愿地实现generatePairs——

      const generatePairs = (n = 0) =>
        chooseN(2, range(0, n))
      

      range 是一个简单的函数,它生成一个从ab 的数组-

      const range = (a = 0, b = 0) =>
        a > b                          // base
          ? []
          : [ a, ...range(a + 1, b) ]  // inductive: a <= b
      

      chooseN 是一个泛型,它从数组a 中生成所有n 大小的样本-

      const chooseN = (n = 0, a = []) =>
        n <= 0                 // base
          ? [[]]
      : a.length <= 0          // inductive: n > 0
          ? []
      : chooseN(n - 1, a)      // inductive: n > 0, non-empty a
          .map(r => [a[0], ...r])
          .concat(chooseN(n, a.slice(1)))
      

      请参阅下面的 generatePairs 在您自己的浏览器中工作 -

      const range = (a = 0, b = 0) =>
        a > b
          ? []
          : [ a, ...range(a + 1, b) ]
      
      const chooseN = (n = 0, a = []) =>
        n <= 0
          ? [[]]
      : a.length <= 0
          ? []
      : chooseN(n - 1, a)
          .map(r => [a[0], ...r])
          .concat(chooseN(n, a.slice(1)))
          
      const generatePairs = (n = 0) =>
        chooseN(2, range(0, n))
          
      const log = x =>
        console.log(JSON.stringify(x))
        
      log(generatePairs(3))
      // [[0,0],[0,1],[0,2],[0,3],[1,1],[1,2],[1,3],[2,2],[2,3],[3,3]]
      
      log(generatePairs(2))
      // [[0,0],[0,1],[0,2],[1,1],[1,2],[2,2]]
      
      log(generatePairs(1))
      // [[0,0],[0,1],[1,1]]
      
      log(generatePairs(0))
      // [[0,0]]

      发电机

      由于组合问题通常涉及较大的解决方案空间,因此通常会懒惰地生成组合。在 JavaScript 中,我们可以使用生成器来做到这一点 -

      const chooseN = function* (n = 0, a = [])
      { if (n <= 0)
          return yield []
      
        if (a.length <= 0)
          return
      
        for (const r of chooseN(n - 1, a))
          yield [a[0], ...r]
      
        yield* chooseN(n, a.slice(1))
      }
      

      请注意此程序与上述程序在结构上的相似性 -

      const chooseN = function* (n = 0, a = [])
      { if (n <= 0)                         // if (n <= 0)
          return yield []                   //   return [[]]
      
        if (a.length <= 0)                  // else if (a.length <= 0)
          return                            //   return []
      
                                            // else return: 
        for (const r of chooseN(n - 1, a))  //   chooseN(n - 1, a).map(r =>
          yield [a[0], ...r]                //     [a[0],...r])
      
        yield* chooseN(n, a.slice(1))       //   .concat(chooseN(n, a.slice(1)))
      }
      

      例如,我们可以编写一个solver 来找到第一对[ a, b ],其中a &gt; 33*a 等于2*b。至关重要的是,在找到第一个解决方案后不会生成任何对 -

      const solver = (size = 0) =>
      { for(const [a, b] of generatePairs(size))
          if (a > 3)
            if (3 * a === 2 * b)
              return [a, b]
      }
      
      console.log(solver(10))
      // [ 4, 6 ]
      

      a = 4b = 6 的解法是正确的:4 &gt; 3 为真且3*4 等于2*6 (12)。

      下面,如果我们愿意,我们可以使用 Array.from 生成整个对数组 -

      const allPairs =
        Array.from(generatePairs(3)) // <-- Array.from exhausts an iterable
      
      console.log(allPairs)
      // [[0,0],[0,1],[0,2],[0,3],[1,1],[1,2],[1,3],[2,2],[2,3],[3,3]]
      

      扩展下面的 sn-p 以使用 JavaScript 的生成器生成对 -

      const range = (a = 0, b = 0) =>
        a > b
          ? []
          : [ a, ...range(a + 1, b) ]
          
      const chooseN = function* (n = 0, a = [])
      { if (n <= 0)
          return yield []
          
        if (a.length <= 0)
          return
          
        for (const r of chooseN(n - 1, a))
          yield [a[0], ...r]
          
        yield* chooseN(n, a.slice(1))
      }
      
      const generatePairs = (n = 0) =>
        Array.from(chooseN(2, range(0, n)))
          
      const log = x =>
        console.log(JSON.stringify(x))
        
      log(generatePairs(3))
      // [[0,0],[0,1],[0,2],[0,3],[1,1],[1,2],[1,3],[2,2],[2,3],[3,3]]
      
      log(generatePairs(2))
      // [[0,0],[0,1],[0,2],[1,1],[1,2],[2,2]]
      
      log(generatePairs(1))
      // [[0,0],[0,1],[1,1]]
      
      log(generatePairs(0))
      // [[0,0]]

      【讨论】:

        猜你喜欢
        • 2022-11-14
        • 1970-01-01
        • 1970-01-01
        • 2013-05-29
        • 1970-01-01
        • 2020-02-10
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多