【问题标题】:How to `reduce` over an object?如何在对象上“减少”?
【发布时间】:2019-08-09 00:33:52
【问题描述】:

我想知道如何在对象而不是数组上使用一些reduce 逻辑。类似于迭代由

表示的元组

[ object_property, property_value ])。

我尝试了一些类似的代码

var obj = { foo: 'bar', bar: 'baz' };
Array.prototype.reduce.call(obj, function(prev, val) {
    console.log('new iteration');
    // whatever code ...
    return prev;
}, []);

但它不执行任何迭代。我不明白为什么。

可能是因为对象属性不可枚举?

有没有办法在对象上运行 reduce 函数?

注意:没有特定的最终目的;我正在探索什么是可能的或更好的模式。

【问题讨论】:

  • Array.prototype.reduce() 假定上下文具有 length 属性和键 [0..length - 1]
  • 预期输出是什么?
  • 没有预期的输出;那不是问题。我想知道是否可以使用reduce进行迭代,不管回调中的操作是什么。
  • 另外reduce 期望你的回调returns 是累加器的新值。我认为你根本不应该在这里使用reduce。
  • 在对象中运行reduce时你想完成什么?期望的最终结果是什么?减少的目标是获得一个独特的价值。如果你想迭代 .map 就更合适了。

标签: javascript arrays reduce enumerable


【解决方案1】:

像reduce() 这样的数组方法只能对数组或类似数组的对象进行操作(带有length 和数字属性)。

您可以调用Object.values() 来获取对象属性值的数组。

【讨论】:

    【解决方案2】:

    您可以在Object.keys() 函数返回的数组上运行reduce() 方法。它看起来像这样:

    var obj = { foo: 'fooValue', bar: 'barValue' };
    var str = Object.keys(obj).reduce((accum, key)=>{
        return accum + obj[key];
    }, '');
    // str = 'fooValuebarValue';
    

    【讨论】:

      【解决方案3】:

      你可以使用 Object.keys(obj) 将为您提供该数组上的属性名称数组,您可以应用任何数组方法(预定义) 像这样

      var obj = { foo: 'bar', bar: 'baz' };
      var prev=[] //let say prev is array in which you want to store some property value
      
      Object.keys(obj).reduce(function(element) {
          // you can have condition here as well
          prev.push(obj[element]);
      });

      但要小心,如果你只是想填充另一个数组,那么你可以使用其他数组方法,如 filter、map、forEach(仅用于学习目的,因为它类似于 for 循环) 这是有道理的。

      【讨论】:

        【解决方案4】:

        几个错误。

        • obj 不是数组。使用 .values()
        • prev.push的结果不是数组,是push方法的结果是1(整数);
        • 没有 var 可以得到最终结果。

        这是一个工作示例:

        var obj = { foo: 'bar', bar: 'baz' };
        var res = Array.prototype.reduce.call(Object.values(obj), function(prev, val) {
            prev.push(val);
            return prev;
        }, []);
        console.log(res);

        我不知道你为什么使用Array.prototype.reduce.call。没有必要这样称呼它。也许您正在尝试使用 js 或其他东西。 prev 也不是一个好名字。请记住,它会累积价值,而不仅仅是先前交互的价值。无论如何,这是一种更简单的方法:

        var obj = { foo: 'bar', bar: 'baz' };
        var res = Object.values(obj).reduce((acc, val)=>{
            acc.push(val); 
            return acc;
        }, []);
        console.log(res);

        但如果这是您想要的答案,则根本不需要 reduce。看:

        var obj = { foo: 'bar', bar: 'baz' };
        console.log(Object.values(obj));

        【讨论】:

        • 所有正确答案,但专注于错误的事情。不过,我修复了返回值,谢谢。问题是关于如何(如果可能)对对象运行归约;这与获取对象值无关。是的:这个问题是因为我正在尝试使用 Javascript,而这个问题纯粹是出于好奇。关于命名的注释也是正确的,但我明确选择不将注意力集中在回调内部,所以我命名它只是为了强调它作为累加器的作用。顺便说一句,imo 正确答案是有关缺少的length 属性的详细信息。
        猜你喜欢
        • 1970-01-01
        • 2019-07-20
        • 2017-05-09
        • 1970-01-01
        • 1970-01-01
        • 2022-11-09
        • 2010-12-07
        • 1970-01-01
        • 2019-03-26
        相关资源
        最近更新 更多