js基础练习题 柯里化
题目描述
已知 fn 为一个预定义函数,实现函数 curryIt,调用之后满足如下条件:
1、返回一个函数 a,a 的 length 属性值为 1(即显式声明 a 接收一个参数)
2、调用 a 之后,返回一个函数 b, b 的 length 属性值为 1
3、调用 b 之后,返回一个函数 c, c 的 length 属性值为 1
4、调用 c 之后,返回的结果与调用 fn 的返回值一致
5、fn 的参数依次为函数 a, b, c 的调用参数
1、返回一个函数 a,a 的 length 属性值为 1(即显式声明 a 接收一个参数)
2、调用 a 之后,返回一个函数 b, b 的 length 属性值为 1
3、调用 b 之后,返回一个函数 c, c 的 length 属性值为 1
4、调用 c 之后,返回的结果与调用 fn 的返回值一致
5、fn 的参数依次为函数 a, b, c 的调用参数
示例1
输入
var fn = function (a, b, c) {return a + b + c}; curryIt(fn)(1)(2)(3);
输出
6
代码
1
2
3
4
5
6
7
8
9
|
function curryIt(fn) { return function a(xa){ return function b(xb){ return function c(xc){ return fn.call( this ,xa,xb,xc); }; }; }; } |
要点
“柯里化”就像某些官员的把戏,官员要弄7个老婆,碍于国策(一夫一妻)以及年老弟衰,表面上就1个老婆,实际上剩下的6个暗地里消化。
柯里化是把接受多个参数的函数变换成接受一个单一参数(最初函数的第一个参数)的函数,并且返回接受余下的参数且返回结果的新函数的技术。简单理解题目意思,就是指,我们将预定义的函数的参数逐一传入到curryIt中,当参数全部传入之后,就执行预定义函数。于是,我们首先要获得预定义函数的参数个数fn.length,然后声明一个空数组去存放这些参数。返回一个匿名函数接收参数并执行,当参数个数小于fn.length,则再次返回该匿名函数,继续接收参数并执行,直至参数个数等于fn.length。最后,调用apply执行预定义函数。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
|
function curryIt(fn) { //获取fn参数的数量 var n = fn.length; //声明一个数组args var args = []; //返回一个匿名函数 return function(arg){ //将curryIt后面括号中的参数放入数组 args.push(arg); //如果args中的参数个数小于fn函数的参数个数, //则执行arguments.callee(其作用是引用当前正在执行的函数,这里是返回的当前匿名函数)。 //否则,返回fn的调用结果 if (args.length < n){ return arguments.callee; } else return fn.apply( "" ,args); } } |
不用 arguments.callee 的方法,用变量名代替了,大同小异:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
|
function curryIt(fn) { var length = fn.length, args = []; var result = function (arg){ args.push(arg); length --; if (length <= 0 ){ return fn.apply( this , args); } else { return result; } } return result; } |
注:这些都是通过别人的讨论得出来的,我只是把我觉得好的汇总。