函数柯里化(Currying)是一种将接受多个参数的函数转化为一系列接受单一参数的函数过程。反柯里化(Uncurrying)则是将一个接受单一参数的函数转化为接受多个参数的函数过程。
在 JavaScript 中,可以使用以下代码实现函数柯里化:
function curry(fn) {
return function curried(...args) {
if (args.length >= fn.length) {
return fn.apply(this, args);
} else {
return function(...args2) {
return curried.apply(this, args.concat(args2));
}
}
}
}
以上代码定义了一个 curry
函数,它接受一个函数作为参数,并返回一个新的函数。这个新函数会在参数数量不足时返回一个新的函数,直到参数数量足够为止,然后执行原始函数。使用该函数时,可以这样写:
function add(a, b, c) {
return a + b + c;
}
const curriedAdd = curry(add);
console.log(curriedAdd(1)(2)(3)); // 6
console.log(curriedAdd(1, 2)(3)); // 6
console.log(curriedAdd(1)(2, 3)); // 6
可以看到,curry
函数能够将 add
函数转换成一个可以接受单个参数的函数序列。
反柯里化则可以使用以下代码实现:
Function.prototype.uncurry = function() {
const fn = this;
return function() {
return Function.prototype.call.apply(fn, arguments);
}
}
以上代码定义了一个 uncurry
函数,它可以被所有函数继承。使用该函数时,可以这样写:
const obj = {
name: 'John Doe',
greet(greeting) {
return `${greeting}, ${this.name}!`;
}
}
const uncurriedGreet = obj.greet.uncurry();
console.log(uncurriedGreet(obj, 'Hello')); // Hello, John Doe!
可以看到,uncurry
函数能够将一个方法转换成一个可以接受多个参数的函数。