函数柯里化

什么是函数柯里化?

百度百科:在计算机科学中,柯里化(Currying)是把接受多个参数的函数变换成接受一个单一参数(最初函数的第一个参数)的函数,并且返回接受余下的参数且返回结果的新函数的技术。通俗点说就是将一个函数拆分成多个函数,是固定部分参数,返回一个接受剩余参数的函数,也称为部分计算函数,目的是为了缩小适用范围,创建一个针对性更强的函数。来个简单的例子

1 // 实现一个简单的加法
2 function add(a,b){return a+b}
3 add(1,2);
4 // 用柯里化实现
5 const currying = (x) => {
6      return (y) => {return x+y}
7 }
8 console.log(currying(1)(2)) // 3

这里就是使用柯里化把add函数拆分成了两个函数,currying首次执行返回一个新的函数,然后再次调用返回结构,返回一个函数的特征就是上一章所说到的高阶函数,柯里化函数就是高阶函数的一种。这里就会有人提问了,为什么要那么费劲实现add函数?有道经典的面试题实现add(1)(2)(3)(4)=10;

 1 // 我们可以这样理解调用add(1)时返回一个函数fn,然后执行fn(2)依次被调用,当执行到最后一次返回结果
 2 function add(num){
 3     var sum=num;
 4     var fn=function(v){
 5         sum+=v;
 6         return fn
 7     }; 
 8     fn.toString=function(){
 9         return sum
10     };
11     return fn
12 }
13 console.log(add(1)(2)(3)(4)) // 10
14 // 执行add(1)时返回了fn函数给2,3,4执行,同时定义了fn的toString方法,
15 // 每个对象的toString和valueOf方法都可以被改写,每个对象执行完毕,如果被用以操作JavaScript解析器就会自动调用对象的toString或者valueOf方法
16 // 利用toString隐式调用的特性,当最后执行时隐式调用,并计算最终的值返回

面试题的内容还有 add(1)(1,2,3)(2)=9 这样的形式,我们上面的方法就没办法执行出正确的答案了,下面来优化一下

 1 function add(){
 2   var args = [...arguments];
 3   var fn=function(){
 4       args.push(...arguments);
 5       return fn
 6   }; 
 7   fn.toString=function(){
 8       return args.reduce(function (a, b) {
 9           return a + b;
10       });
11   };
12   return fn
13 }
14 console.log(add(1)(1,2,3)(2).toString())

以上就是函数柯里化的简单实现。继续来实现一些例子来看看柯里化的好处

 1 // 实现一个判断数据类型的方法
 2 const checktype = function(type, content) {
 3     return Object.prototype.toString.call(content) === `[object ${type}]`;
 4 }
 5 checktype('Number',2); // true
 6 // 这种方法总是要把type参数传过去,如果写错了就会影响到正确的结果了,可以考虑下如何做到把“Number“做到复用
 7 
 8 const curry = function(type){
 9     return function(content){
10         return Object.prototype.toString.call(content) === `[object ${type}]`;
11     }
12 }
13 const isNumber =  curry('Number');
14 isNumber(3) // true 
15 // 这里就实现参数的复用了,这样的实现给之后的调用带来了很大的便利

 

posted @ 2020-05-28 15:08  xfcao  阅读(246)  评论(0编辑  收藏  举报