Unlimited Plugins, WordPress themes, videos & courses! Unlimited asset downloads! From $16.50/m
Advertisement
  1. Code
  2. JavaScript

Understanding Function Currying in JavaScript—and When to Use It

by
Read Time:7 minsLanguages:

In this article, we’ll discuss function currying in JavaScript, which is an advanced concept in functional programming.

JavaScript is one of the core technologies of the web. The majority of websites use it, and all modern web browsers support it without the need for plugins. In this series, we’re discussing different tips and tricks that will help you in your day-to-day JavaScript development.

What Is Function Currying?

Function currying is an advanced technique for working with JavaScript functions. In fact, it’s not limited to JavaScript—it’s also used in other programming languages.

As per Wikipedia:

Currying is the technique of converting a function that takes multiple arguments into a sequence of functions that each take a single argument.

In other words, currying is just the transformation of a function that takes multiple arguments into a sequence of nested functions that take a single argument. For example, for a function f that takes three arguments, you would call it like f(arg1, arg2, arg3). When you use function currying, you would be able to call it like f(arg1)(arg2)(arg3)

Let’s assume that you have a function that takes three arguments, as shown in the following snippet.

To call the above function, you would use the following syntax.

Now, let’s see a simplistic implementation of a curried version of the above function:

And with that, you can call the fooBarCurriedVersion function with the following syntax:

One advantage of this is that you can separate the passing of each argument to the function. For example, if you only know the value of arg1 at some point in the code, you could call the curried function with just that argument and pass the resulting function on to the rest of your code. 

Let’s try to understand how it’s executed.

Firstly, the fooBarCurriedVersion(arg1) statement is executed, and it returns the callable which takes a single argument. Next, the callable function which is returned by the fooBarCurriedVersion function is called with the arg2 argument, and it again returns the callable, which takes a single argument. Finally, the callable function returned by the previous step is called with the arg3 argument.

It’s important to note that since all functions are closures, argument values that are passed are preserved between function calls. So if you call once an argument to a curried function is initialized, that function instance will have that argument fixed, no matter what other instances you create later.

You can also call the curried function as shown in the following snippet. It works identically to fooBar(arg1)(arg2)(arg3).

As you can see, when we are using function currying, the function takes a single argument and returns a callable function, which takes the next argument and returns another callable function, and so on until all arguments are exhausted.

In fact, you can also call it as shown in the following snippet.

So those are the basics of function currying in JavaScript. In the next section, we’ll go through a real-world example to demonstrate how it works.

A Real-World Example

Now, you know how function currying works in JavaScript. In this section, we’ll see how you can use it in your day-to-day JavaScript development.

First of all, let’s look at the following function, which calculates the final price of a product after adding necessary charges and applying a discount.

Now, you could call this function as shown in the following snippet.

As you can see, we’re fetching the discount rate from the configuration, so it’s going to be fixed every time. So we could avoid passing it in the third argument every time we call the calFinalPrice function, if we create a curried version of the function as shown in the following snippet.

Firstly, we’ve implemented the calFinalPriceWithDiscount function, which is the curried version of the calFinalPrice function. In the first argument of the calFinalPriceWithDiscount function, we’ve passed the discount rate, which will be used later on to calculate the final price of the product.

The discVersionFunc variable holds the callable, which takes two arguments: actual price and charges. Since the discVersionFunc version wraps the discount rate in a closure, you don’t need to pass it every time you need to calculate the final price of the product.

Finally, you can calculate the final price of a product by passing the price and charge values, as shown in the above snippet.

Now, let’s say you want to provide a special discount for some duration. You can still use the calFinalPriceWithDiscount function, as shown in the following snippet.

As you can see, the main benefit of function currying is that when you need to call a function with the same parameters repeatedly, you can reuse and refactor your code, which becomes much easier to maintain over time.

When to Use Function Currying

Function currying can be helpful in some cases, but it's not something you want to do with all your functions by default. Consider function currying when it helps you with one of these goals:

  • writing cleaner code
  • removing expensive computations
  • creating a single-argument function for map or forEach

Write Cleaner Code With Less Repetition

Sometimes function currying can simplify your code. Suppose you have a logging function logToFile(filename, appname, text) that logs some text to a file. To make it easier to add logging statements in your code, you might like to set the filename and app name once and then simply write something like log(text). To achieve that, you can create a curried version of the logging function:

Remove Expensive Computations

Another use for curried functions is to save expensive computations—like file I/O or database reads. For example, say you have the following function:

Suppose we wanted to read a number of attributes from the same function in a row. This would mean reading the same database record a number of times, which is wasteful and slow. We could rewrite the getItemAttribute function with currying to make this more efficient:

Create a Single-Argument Function for map or forEach

Using the map and forEach methods, you can apply a function to each element of an array. However, these methods expect the function to have a certain signature—usually you'll just want to use a method with a single parameter. Using function currying, you can create a version of any function that can be used with map or forEach.

You can learn more about map and forEach in one of our other JavaScript tutorials.

Conclusion

Today, we discussed how function currying works in JavaScript. We also went through a couple of real-world examples to understand the practical applications of function currying in JavaScript.

Advertisement
Advertisement
Looking for something to help kick start your next project?
Envato Market has a range of items for sale to help get you started.