Javascript 为什么要在“array#reduce”中返回一个函数,而不是只传递一个函数

Javascript 为什么要在“array#reduce”中返回一个函数,而不是只传递一个函数,javascript,ecmascript-6,reduce,Javascript,Ecmascript 6,Reduce,几周前,关于如何重新排列数据结构,收到了以下解决方案: var data = [{ timeline_map: { "2017-05-06": 770, "2017-05-07": 760, "2017-05-08": 1250 } }, { timeline_map: { "2017-05-06": 590, "2017-05-07": 210, "2017-05-08": 300 } }, { timeline_map: { "2017-05-06": 890, "2017-05-07":

几周前,关于如何重新排列数据结构,收到了以下解决方案:

var data = [{ timeline_map: { "2017-05-06": 770, "2017-05-07": 760, "2017-05-08": 1250 } }, { timeline_map: { "2017-05-06": 590, "2017-05-07": 210, "2017-05-08": 300 } }, { timeline_map: { "2017-05-06": 890, "2017-05-07": 2200, "2017-05-08": 1032 } }],
    grouped = data.reduce(function (hash) {
        return function (r, o) {
            Object.keys(o.timeline_map).forEach(function (k) {
                if (!hash[k]) {
                    hash[k] = [k];
                    r.push(hash[k]);
                }
                hash[k].push(o.timeline_map[k]);
            });
            return r;
        };
    }(Object.create(null)), []);

console.log(grouped);
然而,再看一遍,我并不完全确定这是如何工作的 我以前从未见过在reduce中返回函数的概念。显然,这是可行的,所以一定有一些原因,但我想澄清一下


在这个
reduce
应用程序中返回函数如何“工作”实际上,当您调用函数
函数(散列){
时,它会立即执行,而不是传递,并返回一个回调,该回调传递给
reduce
,然后用该回调调用
reduce
,很简单

编辑

.reduce(function(hash){...}, []) //meant passing the callback
.reduce(function(hash){...}**(Object.create(null))**, []) //meant executing the callback
那么如果

function someFn(hash) {return 10}
.reduce(someFn("abc"))

这意味着
.reduce
将使用
10
调用,对吗?因为
someFn
将首先调用,然后返回
10
。因此,类似地,如果
someFn
返回回调会怎么样?
reduce
将使用该回调作为参数调用。因此,这里的情况与您的情况相同,只是不同t是函数
someFn
不是更早创建的,它是立即创建和调用的。(如果您不知道立即调用函数的概念)

基本上,它是一个哈希表上的闭包,值为真正的空对象

grouped = data.reduce(function (hash) {
    return function (r, o) {
        // ...
    };
}(Object.create(null)), []);
它对变量
hash
使用一个函数,该变量的作用域在回调函数中

function (hash) {
    return function (r, o) {
        // ...
    };
}(Object.create(null))

不幸的是,这个答案非常神秘。它应该是:

var data = [{ timeline_map: { "2017-05-06": 770, "2017-05-07": 760, "2017-05-08": 1250 } }, { timeline_map: { "2017-05-06": 590, "2017-05-07": 210, "2017-05-08": 300 } }, { timeline_map: { "2017-05-06": 890, "2017-05-07": 2200, "2017-05-08": 1032 } }];

function group(data) {
  const hash = {};

  return data.reduce(function(r, o) {
    Object.keys(o.timeline_map).forEach(function (k) {
      if (!hash[k]) {
        hash[k] = [k];
        r.push(hash[k]);
      }
      hash[k].push(o.timeline_map[k]);
    });
    return r;
  }, []);
}
console.log(group(data));

所提供的解决方案涉及到一种不明智的尝试,即通过一个自调用函数来避免分配
散列
对象,该函数将其作为一个参数。

你能用更多的话来解释这一点吗?对于一个愚蠢的人,请?@1252748是一个立即调用函数,它立即执行并重新运行另一个回调。ch如果您还有疑问,请选择我的答案。我只是不明白为什么它需要成为一种生活。reduce的回调不会立即被调用吗?关键是没有理由这样做。与其解释这些扭曲,不如提供一个不需要它们的解决方案版本,让普通人能够理解nd.@torazaburo,是的,也许不需要它,但我对助手变量使用了一种自包含的方法,只用于reduce的内部回调。“Simple”是relative.yup,这就是为什么添加了更高版本来从基层解释的原因。+1作为前提,但为什么不使用
const hash=Object.create(null)
避免与
对象的属性发生冲突。原型
?晦涩难懂是一个糟糕的词语选择。你是否应该使用解决方案取决于解决方案模型的内部一致性和正确解决问题的方式。如果你不理解某件事,那么无知就是你自己的错,你将因此受到惩罚不知道。与其说是挑战,不如说是对哑巴的侮辱。@Arrow我将坚持使用“奥术”。我是一名经验丰富的JS程序员,甚至在看这段代码时,我也做了双重考虑。