【问题标题】:JavaScript reduce can't handle Math functions?JavaScript reduce 不能处理数学函数?
【发布时间】:2011-12-07 17:45:23
【问题描述】:

我正在尝试一项显而易见的任务:

var maxVal = [ 1, 2, 3, 4, 5 ].reduce( Math.max, 0 );

然后得到:

NaN

结果。为了使它工作,我必须以这种方式创建一个匿名函数:

var maxVal = [ 1, 2, 3, 4, 5 ].reduce( function ( a, b ) { 
                                           return Math.max(a, b);
                                       }, 0 );

谁能告诉我为什么?两者都是接受两个参数并且都返回一个值的函数。有什么区别?

另一个例子可能是这样的:

var newList = [[1, 2, 3], [4, 5, 6]].reduce( Array.concat, [] );

结果是:

[1, 2, 3, 0, #1=[1, 2, 3], #2=[4, 5, 6], 4, 5, 6, 1, #1#, #2#]

我只能在这个形状下在 node.js 中运行这个例子(在我现在使用的 node.js v4.12 中数组没有 concat):

var newList = [[1, 2, 3], [4, 5, 6]].reduce( [].concat, [] );    

然后得到这个:

[ {}, {}, 1, 2, 3, 0, [ 1, 2, 3 ], [ 4, 5, 6 ], 4, 5, 6, 1, [ 1, 2, 3 ], [ 4, 5, 6 ] ]

为什么会这样?

【问题讨论】:

    标签: javascript node.js reduce higher-order-functions


    【解决方案1】:

    由于Math.max 接受多个参数,您可以通过apply 函数将数组转换为参数列表。

    var maxVal = Math.max.apply(Math, [ 1, 2, 3, 4, 5 ]);
    

    See warnings here 关于这种技术的局限性。

    【讨论】:

      【解决方案2】:

      另一种将数组减少到最大值的方法:

      var maxVal = [ 1, 2, 3, 4, 5 ].reduce(function(a,b){return a>b?a:b});
      

      (说明reduce的工作原理,并不是说它是从数组中获取最大数的最佳方法)

      【讨论】:

        【解决方案3】:

        传递给reducetakes more than 2 arguments的函数:

        • previousValue
        • currentValue
        • index
        • array

        Math.max 将评估 所有 参数并返回最高值:

        Math.max(1, 2, 3, 4) === 4;
        

        所以在将Math.max 传递给reduce 的情况下,它将返回所传递的4 个参数中的最大值,其中一个是数组。传递数组将使Math.max 返回NaN,因为数组不是数字。这是规范(15.8.2.11):

        给定零个或多个参数,对每个参数调用 ToNumber 并返回结果值中的最大值。

        ...

        如果任何值为 NaN,则结果为 NaN

        ToNumber 将为数组返回 NaN

        所以使用Math.max 减少最终会返回NaN

        【讨论】:

        • 另一种解决方案可以是:Math.max.apply(null, [1, 2, 3, 4, 5]);
        • 谢谢!!现在很清楚了。我编辑了我的问题,但你用 reduce 回答了我的两个问题!现在很酷。
        • 真是一堆废话,令人难以置信的缺乏远见。 ECMA 如何reduce(max) 视为人们会写的东西?他们需要加强他们的功能性游戏。
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2011-05-24
        • 1970-01-01
        • 2015-09-05
        • 2022-01-13
        • 1970-01-01
        • 1970-01-01
        • 2023-03-08
        相关资源
        最近更新 更多