使用整数数组的递归。

3
编写一个函数,根据给定的整数数组和正整数 X,返回所有大于 X 的奇数元素的乘积。使用递归!
我尝试了这个:
function result(arr, x) {
    if (arr.length <= 0) {
        return 0;
    }

    if (arr[0] > x && arr[0] % 2 === 1) {
        return arr[0] + result(arr.slice(1));
    }

    return result(arr.slice(1));
}

console.log(result([3, 2, 3, 4, 5, 6, 7, 8, 9], 1));

答案是3。 第一次迭代之后(x变成未定义)。


欢迎来到Stack Overflow。这个社区是为了帮助你,而不是为了完成你的任务。 - tmsbrndz
2
请将以下与编程相关的内容从英文翻译成中文。只返回翻译后的文本:请将此添加到问题中,并附上错误信息。 - Nina Scholz
3
产品不等于总和,否则看起来已经很好了。请将其编辑到问题中。 - Jonas Wilms
2
关于 x 变成未定义的问题:当您进行调用时,请将 x 传递给 result(..., x) - Jonas Wilms
3个回答

3

试试这样:

function result(arr, x) {
    if (arr.length <= 0) {
        return 0;
    }

    if (arr[0] > x && arr[0] % 2 === 1) {
        return arr[0] + result(arr.slice(1), x);
    }

    return result(arr.slice(1), x);
}

console.log(result([3, 2, 3, 4, 5, 6, 7, 8, 9], 1));

你已经非常接近了!当再次调用 result 函数时,你只需要将变量 x 的值传递给它。之后,它会返回正确的答案:3 + 3 + 5 + 7 + 9 = 27

编辑: 需要每次在函数调用中传递变量 x,因为变量作用域的原因。到目前为止,result 函数只知道直接传递给它的变量。

如果 x 是一个常量,另一种处理方式是在开头定义 x,然后将函数更改为仅接受数组:

    const x = 1;

    function result(arr) {
        if (arr.length <= 0) {
            return 0;
        }

        if (arr[0] > x && arr[0] % 2 === 1) {
            return arr[0] + result(arr.slice(1));
        }

        return result(arr.slice(1));
    }

    console.log(result([3, 2, 3, 4, 5, 6, 7, 8, 9]));

如果x不是一个常量,但你只想将这个值传入递归函数一次,你也可以通过子函数实现,示例如下:

    function result(arr, x) {
      function recur(arr) {
        if (arr.length <= 0) {
          return 0;
        }

        if (arr[0] > x && arr[0] % 2 === 1) {
          return arr[0] + recur(arr.slice(1));
        }

        return recur(arr.slice(1));
      }

      return recur(arr);
    }

    console.log(result([3, 2, 3, 4, 5, 6, 7, 8, 9], 1));

在这种情况下,recur函数可以访问直接传递给它的变量(arr)以及其父函数(x)的变量。使用最近可用作用域的arr值。这种方法可以帮助简化复杂的递归函数。

1
不客气 :) 很高兴它对你有用。我已经编辑了答案,试图解释它并展示如何更改函数,以便您不需要每次传递 x 的值。 - sbgib

1
您正在尝试计算“总和”。从[3, 2, 3, 4, 5, 6, 7, 8, 9]中大于1的奇数的乘积为3 * 3 * 5 * 7 * 9(= 2835)。以下是过滤大于1的奇数,然后使用递归(子)函数计算乘积的代码片段。使用子函数是一种优化技巧。您也可以使用Array.reduce

function productOfUnEvenValuesGreaterThanX(arr, x) {
    // filter desired values
    const oddAndGreaterThanX = arr.filter(v => v > x && ~~(v % 2));
    //                                                  ^ bitwise to determine odd 
    
    // calculate the product recursively
    function product(arrx, y) {
      return arrx.length 
        ? product(arrx.slice(1), (arrx.shift() || 1) * y)
        : y;
    }
    
    return !oddAndGreaterThanX.length ? 0 : product(oddAndGreaterThanX, x);
}

console.log(productOfUnEvenValuesGreaterThanX([3, 2, 3, 4, 5, 6, 7, 8, 9], 1));
console.log(productOfUnEvenValuesGreaterThanX([2, 4, 6, 8], 1));

// alternatively you can use a reducer
function productOfUnEvenValuesGreaterThanXReducer(arr, x) {
  return arr.reduce( (acc, val) =>
    val > x && ~~(val % 2) 
      ? (acc || 1) * val 
      : acc, 0 );
}

console.log(productOfUnEvenValuesGreaterThanXReducer([3, 2, 3, 4, 5, 6, 7, 8, 9], 1));
console.log(productOfUnEvenValuesGreaterThanXReducer([2, 4, 6, 8], 1));


1

另一种递归方法,不改变数组本身。

function sumResult(arr, x, i = 0, sum = 0) {
  if ([0, i].includes(arr.length)) {
    return sum;
  }

  const updated = sum + (arr[i] > x && arr[i] % 2 === 1 ? arr[i] : 0);

  return sumResult(arr, x, i + 1, updated);
}

console.log('sum: ', sumResult([3, 2, 3, 4, 5, 6, 7, 8, 9], 1));




function productResult(arr, x, i = 0, product = 1) {
  if ([0, i].includes(arr.length)) {
    return product;
  }

  const updated = product * (arr[i] > x && arr[i] % 2 === 1 ? arr[i] : 1);

  return productResult(arr, x, i + 1, updated);
}

console.log('product: ', productResult([3, 2, 3, 4, 5, 6, 7, 8, 9], 1));


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接