← Back to all posts

Currying in JavaScript

Sharpen Currying Skills

3 parts
  1. Higher-order functions for currying in JavaScript
  2. Predicate Functions in JavaScript
  3. Currying in JavaScript
Currying in JavaScript

In this post, I want to keep things simple: what currying is, how it relates to partial application, and why it can be useful in real JavaScript code.

What is currying?

Currying transforms a function of many arguments into a chain of one-argument functions.

// uncurried
const add = (a, b) => a + b;

// curried
const addC = a => b => a + b;

Instead of passing all arguments at once, you pass them one at a time. Each call returns a new function that waits for the next argument until the final result can be produced.

A small example makes it easier:

const add = a => b => a + b;
// The you can call it like this:
add(2)(3); // 5

// Or you can partially apply it:
const increment = add(1);
const add5 = add(5);

// And call it later:
increment(4); // 5
add5(10); // 15

Currying vs partial application

These ideas are related, but they are not the same. I used to blur them together, so it is worth separating them clearly. Currying changes the shape of a function. Partial application uses that shape to pre-fill some arguments and get back a more specific function.

Here is a simple example:

const multiply = a => b => a * b; // curried function

const double = multiply(2); // partial application

double(5); // 10

multiply is curried because it takes one argument at a time. double() is the result of partial application because we fixed the first argument to 2 and got back a more specific function.

Why this is useful

The main thing I like about currying is that it helps me build small reusable functions from more general ones.

const replace = regex => replacement => str => str.replace(regex, replacement);

const replaceSpaces = replace(/\s+/g)("-");

replaceSpaces("functional programming in js"); // "functional-programming-in-js"

This is useful when you want to configure a function once and then reuse it in several places without repeating the same arguments over and over.

Exercises

To get the best out of this series, I recommend spending 15-25 minutes solving the exercises on your own, then checking the answers.

1. Curry multiply

Convert this multiply function to curried form:

const multiply = (a, b) => a * b;
Show answer
const multiply = a => b => a * b;

2. Curry replace

Convert this replace function to curried form:

const replace = (regex, replacement, str) => str.replace(regex, replacement);
Show answer
const replace = regex => replacement => str => str.replace(regex, replacement);

3. Explain the first application

Explain in your own words:

  • What does multiply(2) return?
  • Why is that useful?
Show answer

multiply(2) returns a new function that is still waiting for the second argument (b). That is useful because it gives you a reusable function for a more specific job, for example:

const double = multiply(2);
double(5); // 10

Checkpoint

You are ready to continue when you can quickly convert between uncurried and curried forms, and explain how partial application is related but different.

Previous article Predicate Functions in JavaScript