首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >函数编程-然后在链式过滤器/映射调用之间进行()

函数编程-然后在链式过滤器/映射调用之间进行()
EN

Stack Overflow用户
提问于 2019-12-18 15:48:20
回答 7查看 458关注 0票数 0

我解析的数据如下:

代码语言:javascript
运行
复制
getData()
.filter(fn)
.filter(fn2)
.filter(fn3)
.map(fn4)

其中过滤器在概念上是分开的,并执行不同的操作。

为了调试目的,是否有一个JavaScript库或一种包装承诺的方法,以便我可以这样做:

代码语言:javascript
运行
复制
getData()
.filter(fn)
.then((result) => { log(result.count); return result })
.filter(fn2)
.then(debugFn)    // extra chained debug step (not iterating through arr)
.filter(fn3)
.map(fn4)

或者这是反模式?

EN

回答 7

Stack Overflow用户

回答已采纳

发布于 2019-12-18 17:41:32

编辑

经过一些思考,我确信这个问题的https://stackoverflow.com/a/59395969/1244884是由V-for-Vaggelis提供的:只需使用断点即可。

如果您做了适当的函数组合,那么在管道中插入几个tap调用是廉价的、容易的和非侵入性的,但它不会给您提供比断点(以及知道如何使用调试器逐步遍历代码)更多的信息。

无论如何,在x上应用一个函数并按原样返回x,已经有了一个名称:tap。在像ramda.js这样的库中,它被描述为:

使用提供的对象运行给定的函数,然后返回对象。

自从filtermap,..。所有返回新实例,您可能没有其他选择,除了扩展原型。

不过,我们可以找到一种有控制的方法。这就是我的建议:

代码语言:javascript
运行
复制
const debug = (xs) => {
  Array.prototype.tap = function (fn) {
    fn(this);
    return this;
  };
  
  Array.prototype.debugEnd = function () {
    delete Array.prototype.tap;
    delete Array.prototype.debugEnd;
    return this;
  };
 
  return xs;
};

const a = [1, 2, 3];

const b =
  debug(a)
    .tap(x => console.log('Step 1', x))
    .filter(x => x % 2 === 0)
    .tap(x => console.log('Step 2', x))
    .map(x => x * 10)
    .tap(x => console.log('Step 3', x))
    .debugEnd();

console.log(b);

try {
  b.tap(x => console.log('WAT?!'));
} catch (e) {
  console.log('Array prototype is "clean"');
}

如果您能够负担得起像Ramda这样的库,最安全的方法是在您的管道中引入tap

代码语言:javascript
运行
复制
const a = [1, 2, 3];

const transform =
  pipe(
      tap(x => console.log('Step 1', x))
    , filter(x => x % 2 === 0)
    , tap(x => console.log('Step 2', x))
    , map(x => x * 10)
    , tap(x => console.log('Step 2', x))
  );
  
console.log(transform(a));
代码语言:javascript
运行
复制
<script src="https://cdnjs.cloudflare.com/ajax/libs/ramda/0.26.1/ramda.min.js"></script>
<script>const {pipe, filter, map, tap} = R;</script>

票数 2
EN

Stack Overflow用户

发布于 2019-12-18 15:57:51

您可以对Array.prototype进行猴子补丁,但是不推荐使用

只要您只将它用于调试

代码语言:javascript
运行
复制
Array.prototype.debug = function (fn) {
    fn(this);
    return this;
};

// example usage
[1, 2, 3].map(n = > n * 2).debug(console.log).map(n => n * 3);

这不是承诺--您可能不需要异步--但是给您提供了.then-like行为。

票数 2
EN

Stack Overflow用户

发布于 2019-12-18 15:59:04

在内置的对象原型中添加函数是有争议的,因此许多人可能会反对它。然而,如果你真的想做你想做的事情,那可能是唯一的选择:

代码语言:javascript
运行
复制
Object.defineProperty(Array.prototype, "examine", {
  value: function(callback) {
    callback.call(this, this);
    return this;
  }
});

然后,您可以将.examine(debugFn)调用放入.filter()调用链中,正如您所描述的那样。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/59395612

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档