I've been thinking a lot lately about functional programming, and I thought it might be kind of fun to walk through the process of writing a `curry` function.

For the uninitiated, currying refers to the process of taking a function with `n` arguments and transforming it into `n` functions that each take a single argument. It essentially creates a chain of partially applied functions that eventually resolves with a value.

Here's a basic example of how you'd use it:

``````function volume( l, w, h ) {
return l * w * h;
}

var curried = curry( volume );

curried( 1 )( 2 )( 3 ); // 6
``````
###### Disclaimer

This post assumes basic familiarity with closures and higher-order functions, as well as stuff like `Function#apply()`. If you're not comfortable with those concepts, you might want to brush up before reading further.

###### Writing our curry function

The first thing you'll notice is that `curry` expects a function as its argument, so we'll start there.

``````function curry( fn ) {

}
``````

Next, we need to know how many arguments our function expects (called its "arity"). Otherwise, we won't know when to stop returning new functions and give back a value instead.

We can tell how many arguments a function expects by accessing its `length` property.

``````function curry( fn ) {
var arity = fn.length;
}
``````

From there, things get a little bit trickier.

Essentially, every time a curried function is called, we add any new arguments to an array that's saved in a closure. If the number of arguments in that array is equal to the number of arguments that our original function expects, then we call it. Otherwise, we return a new function.

To do that, we need (1) a closure that can retain that list of arguments and (2) a function that can check the total number of arguments and either return another partially applied function or the return value of the original function with all of the arguments applied.

I usually do this with an immediately invoked function called `resolver`.

``````function curry( fn ) {
var arity = fn.length;

return (function resolver() {

}());
}
``````

Now, the first thing we need to do in `resolver` is make a copy of any arguments it received. We'll do that by creating a variable called `memory` that uses `Array#slice` to make a copy of the `arguments` object.

``````function curry( fn ) {
var arity = fn.length;

return (function resolver() {
var memory = Array.prototype.slice.call( arguments );
}());
}
``````

Next, `resolver` needs to return a function. This is what the outside world sees when it calls a curried function.

``````function curry( fn ) {
var arity = fn.length;

return (function resolver() {
var memory = Array.prototype.slice.call( arguments );
return function() {

};
}());
}
``````

Since this internal function is the one that ends up actually being called, it needs to accept arguments. But it also needs to add those to any arguments that might be stored in `memory`. So first, we'll make a copy of `memory` by calling `slice()` on it.

``````function curry( fn ) {
var arity = fn.length;

return (function resolver() {
var memory = Array.prototype.slice.call( arguments );
return function() {
var local = memory.slice();
};
}());
}
``````

Now, lets add our new arguments by using `Array#push`.

``````function curry( fn ) {
var arity = fn.length;

return (function resolver() {
var memory = Array.prototype.slice.call( arguments );
return function() {
var local = memory.slice();
Array.prototype.push.apply( local, arguments );
};
}());
}
``````

Good. Now we have a new array containing all the arguments we've received so far in this chain of partially applied functions.

The last thing to do is to compare the length of arguments we've received with the arity of our curried function. If the lengths match, we'll call the original function. If not, we'll use `resolver` to return yet another function that has all of our current arguments stored in memory.

``````function curry( fn ) {
var arity = fn.length;

return (function resolver() {
var memory = Array.prototype.slice.call( arguments );
return function() {
var local = memory.slice(), next;
Array.prototype.push.apply( local, arguments );
next = local.length >= arity ? fn : resolver;
return next.apply( null, local );
};
}());
}
``````

This can be a little bit difficult to wrap your head around, so let's take it step by step in an example.

``````function volume( l, w, h ) {
return l * w * h;
}

var curried = curry( volume );
``````

Okay, so `curried` is the result of passing `volume` into our `curry` function.

If you look back, what's happening here is:

1. We store the arity of `volume`, which is `3`.
2. We immediately invoke `resolver` with no arguments, which means that for now, its `memory` array is empty.
3. `resolver` returns an anonymous function.

Still with me? Now let's call our `curried` function and pass in a length.

``````function volume( l, w, h ) {
return l * w * h;
}

var curried = curry( volume );
var length = curried( 2 );
``````

Again, here are the steps:

1. What we actually called here was the anonymous function being returned by `resolver`.
2. We made a copy of `memory` (which was empty) and called it `local`.
3. We added our argument (`2`) to the `local` array.
4. Since the length of `local` is less than the arity of `volume`, we call `resolver` again with the list of arguments we have so far. That creates a new closure with a new `memory` array, which contains our first argument of `2`.
5. Finally, `resolver` returns a new function that has access to an outer closure with our new `memory` array.

So what we get back is that inner anonymous function again. But this time, it has access to a `memory` array that isn't empty. It has our first argument (a `2`) inside of it.

If we call our `length` function, the process repeats.

``````function volume( l, w, h ) {
return l * w * h;
}

var curried = curry( volume );
var length = curried( 2 );
var lengthAndWidth = length( 3 );
``````
1. Again, what we actually called was the anonymous function being returned by `resolver`.
2. This time, `resolver` had been primed with some previous arguments. So we make a copy of that array `[ 2 ]`.
3. We add our new argument, `3`, to the `local` array.
4. Since the length of `local` is still less than the arity of `volume`, we call `resolver` again with the list of arguments we have so far – and that returns a new function.

Now it's time to call our `lengthAndWidth` function and get back a value.

``````function volume( l, w, h ) {
return l * w * h;
}

var curried = curry( volume );
var length = curried( 2 );
var lengthAndWidth = length( 3 );

console.log( lengthAndWidth( 4 ) ); // 24
``````

This time, the steps are a little bit different at the end:

1. Once again, what we actually called was the anonymous function being returned by `resolver`.
2. This time, `resolver` had been primed with two previous arguments. So we make a copy of that array `[ 2, 3 ]`.
3. We add our new argument, `4`, to the `local` array.
4. Now the length of `local` is `3`, which is the arity of `volume`. So instead of returning a new function, we return the result of calling `volume` with all of the arguments we've been saving up, and that gives us a value of `24`.
###### Wrapping up

Admittedly, I have yet to find a super compelling use-case for currying in my day-to-day work. But I still think that going through the process of writing functions like this is a great way to improve your understanding of functional programming, and it helps reinforce concepts like closures and first-class functions.

By the way, if you like nerdy JavaScript things and live in the Boston area, I'm hiring at Project Decibel. Shoot me an email.