Last active
January 28, 2019 20:16
-
-
Save ericcornelissen/09e11b331a901c340a05664e85a02b69 to your computer and use it in GitHub Desktop.
Simple and small wrapper to curry functions of any arity
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** | |
* Curry a function of any length. Note that a curried | |
* function accepts only one argument at the time. | |
* | |
* @example <caption>Simple usage</caption> | |
* let addTwoNumbers = curry((x, y) => x + y); | |
* addTwoNumbers(1); // => Function[y => 1 + y] | |
* addTwoNumbers(1)(3); // => 4 | |
* | |
* @example <caption>Incorrect usage</caption> | |
* let addTwoNumbers = curry((x, y) => x + y); | |
* addTwoNumbers(1, 3); // => Function[y => 1 + y] | The second argument is ignored | |
* addTwoNumbers(1, 3)(3); // => 4 | |
* | |
* @param {Function} fn The function to curry. | |
* @return {Function} The curried function. | |
* @license The-Unlicense | |
*/ | |
function curry(fn) { | |
// Check if the provided argument is a function | |
if (typeof fn !== 'function') throw Error('Curry should be provided with a function'); | |
// Get the arity of the function to curry | |
const arity = fn.length; | |
// Return the return value of resolver() which is the curried function | |
return (function resolver() { | |
// Create *local* memory to allow for reuse of the curried function | |
const memory = Array.from(arguments); | |
// Return the curried function | |
return function(x) { | |
// Add the provided argument to the memory | |
let args = memory.slice(0); | |
args.push(x); | |
// Call fn if enough arguments have been provided, otherwise return | |
// another curried function | |
const next = args.length >= arity ? fn : resolver; | |
return next.apply(null, args); | |
}; | |
}()); | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment