当前位置:首页 > Web开发 > 正文

JS高阶编程技巧

2024-03-31 Web开发

let fn1 = function (x) { return x + 10; }; let fn2 = function (x) { return x * 10; }; let fn3 = function (x) { return x / 10; };

  console.log(fn3(fn1(fn2(fn1(6)))));

这是几个简单的运算要领,但想输出的是一个多层函数嵌套的运行功效,即把前一个函数的运行功效赋值给后一个函数,固然我们可以写成一下这样:

let x = fn1(6); x = fn2(x); x = fn1(x); x = fn3(x);

但此刻我就想用一个函数解决这种问题,形如:

compose(fn1, fn2, fn1, fn3)(6);

这个compose函数就是这篇文章介绍的——函数挪用的扁平化,即把层级嵌套的那种函数挪用(一个函数的运行功效看成实参传给下一个函数的这种操纵)扁平化,这就是compose函数。

那么下面就是开始实现这个函数:

首先我们看参数,,需要给出不确定个数的函数:

function compose(...funcs) { //=>funcs:通报的函数调集 }

compose函数执行后跟个(),说明函数执行完再执行一个函数,即函数执行完会返回一个新函数,而且也会给出第一次挪用函数时的参数:

function compose(...funcs) { //=>funcs:通报的函数调集 return function proxy(...args) {   //=>args:第一次挪用函数通报的参数调集 } }

继续往下进行,我们需要判断给出的函数调集的个数,如果没有给函数,我们只需将后一个的参数返回,如果只给出一个函数,我们只需把后一个的参数赋给这个函数去执行即可:

function compose(...funcs) { //=>funcs:通报的函数调集 return function proxy(...args) { //=>args:第一次挪用函数通报的参数调集 let len = funcs.length; if (len === 0) { //=>一个函数都不需要执行,直接返回ARGS return args; } if (len === 1) { //=>只需要执行一个函数,把函数执行,把其功效返回即可 return funcs[0](...args); } }; }

如果给出的参数调集是两个及以上,那就是把前一个函数的执行功效赋给后一个函数,说到这,应该会想到一个满足这个需求的数组要领——reduce:

function compose(...funcs) { //=>funcs:通报的函数调集 return function proxy(...args) { //=>args:第一次挪用函数通报的参数调集 let len = funcs.length; if (len === 0) { //=>一个函数都不需要执行,直接返回ARGS return args; } if (len === 1) { //=>只需要执行一个函数,把函数执行,把其功效返回即可 return funcs[0](...args); } return funcs.reduce((x, y) => { }); }; }

但这里需要注意的是,第一次执行的时候,参数x是个函数,之后再执行的时候x是个函数执行的功效,所以需要进行判断:

function compose(...funcs) { //=>funcs:通报的函数调集 return function proxy(...args) { //=>args:第一次挪用函数通报的参数调集 let len = funcs.length; if (len === 0) { //=>一个函数都不需要执行,直接返回ARGS return args; } if (len === 1) { //=>只需要执行一个函数,把函数执行,把其功效返回即可 return funcs[0](...args); } return funcs.reduce((x, y) => { return typeof x === "function" ? y(x(...args)) : y(x) }); }; }

这样,compose函数完成。

固然,redux源码中的compose.js也可以实现一开始想要的效果:

export default function compose(...funcs) { if (funcs.length === 0) { return arg => arg } if (funcs.length === 1) { return funcs[0] } return funcs.reduce((a, b) => (...args) => a(b(...args))) }

但它和我们写的compose函数有些差别,它执行的挨次是函数调集中的函数从后往前执行,所以功效也会差别:

compose(fn1, fn2, fn1, fn3)(6)); //=> 用第一个compose执行的功效是17,用redux的执行功效是116

JS高阶编程技巧--compose函数

温馨提示: 本文由Jm博客推荐,转载请保留链接: https://www.jmwww.net/file/web/30002.html