Arrow functions are a relatively new way of writing function expressions in JavaScript. They have been introduced by the ECMAScript 6 specifications and since then become the most popular ES6 feature. Arrow functions allow you to use the fat arrow syntax to quickly define JavaScript functions, with or without parameters. Its biggest advantage is that you can omit curly brackets and the function and return keywords when creating a new JavaScript function.
The syntax might look strange at first, but it’s worth getting familiar with it. Arrow functions are not only time savers but also produce more readable code. Many JavaScript developers already use them on a daily basis, too.
This is how the Mozilla Developer Network defines the basic syntax:
( param1, param2, ..., paramN ) => { statements }
In this tutorial, we’ll have a look into some real-world examples to see how to create arrow functions in different scenarios. We’ll also show you the same code using the older ECMAScript 5 notation so that you can see how the two syntaxes compare to each other.
No Parameters
The simplest arrow function syntax is when the function doesn’t have any parameters. In the example below, the ECMAScript 5 syntax declares a function expression and assigns it to the birthday variable. It outputs a simple text string to the console, saying “Happy birthday!”.
// ES5 syntax with no parameters
var birthday = function() {
return "Happy birthday!";
}
console.log( birthday() );
// Happy birthday!
In the arrow function syntax, the curly brackets and the function and return keywords disappear. Now, the whole function takes just one single line. The empty parentheses indicate that the function doesn’t have any parameters and the fat arrow binds the function body to the (currently non-existing) parameters.
// ES6 syntax with no parameters
var birthday = () => "Happy birthday!";
console.log( birthday() );
// Happy birthday!
One Parameter
Let’s extend the previous example with one parameter, specifically name. The old ES5 syntax takes in one parameter and appends its value to the string to be returned:
// ES5 syntax with one parameter
var birthday = function( name ) {
return "Happy birthday, " + name + "!";
}
console.log( birthday( "John" ) );
// Happy birthday, John!
The arrow function syntax essentially does the same thing. You need to enclose the name parameter within the parentheses before the fat arrow and omit the return keyword in the function block:
// ES6 syntax with one parameter
var birthday = ( name ) => "Happy birthday, " + name + "!" ;
console.log( birthday( "Jane" ) );
// Happy birthday, Jane!
Two Parameters
You can use arrow functions with as many parameters as you want. For instance, here is the same example with two parameters, age and name. Now, the birthday() function requires two inputs to return the string. First, let’s use ECMAScript 5:
// ES5 syntax with two parameters
var birthday = function( age, name) {
return "Happy " + age + "th birthday, " + name + "!";
}
console.log( birthday( 30, "John" ) );
// Happy 30th birthday, John!
And, here’s the same code with the new ES6 notation:
// ES6 syntax with two parameters
var birthday = ( age, name ) => "Happy " + age + "th birthday, " + name + "!";
console.log( birthday( 32, "Jane" ) );
// Happy 32th birthday, Jane!
If the function declaration is too long or takes up multiple lines, you can also enclose it within curly brackets, as you can see it below. However, when you do so, you always have to add the return keyword to the function block, too.
// Same ES6 function enclosed in a function block
var birthday = ( age, name ) => {
return "Happy " + age + "th birthday, " + name + "!"
};
console.log( birthday( 34, "James" ) );
// Happy 34th birthday, James!
Conditional Statements
Arrow functions can also be an excellent choice when you want to use conditional statements inside a function block. The following script defines a simple switcher where the state parameter indicates if the switcher is turned on or off.
// Conditional statement with ES5 syntax
var switcher = function( state ) {
if( state == "on" ) {
return "Switched on!";
} else if ( state == "off" ) {
return "Switched off!";
} else {
return "Switcher not working!";
}
}
console.log( switcher( "on" ) );
// Switched on!
As the if-else block takes up multiple lines, you need to use the return keyword inside each part of the block. Other than that, you can write the arrow function the same way as before:
// Conditional statement with ES6 syntax
var switcher = ( state ) => {
if( state == "on" ) {
return "Switched on!";
} else if ( state == "off" ) {
return "Switched off!";
} else {
return "Switcher not working!";
}
}
console.log( switcher( "off" ) );
// Switched off!
Object Literals
You can also use the arrow function syntax to declare setter functions that let users set the value of object literals. The setBirthday() function below allows users to set the name and age of the person having a birthday:
// Object literal setter with ES5 syntax
var setBirthday = function( name, age ) {
return {
name: name,
age: age
}
}
console.log( setBirthday( "John", 30 ) );
// Object { name: "John", age: 30 }
By making use of the arrow function notation, it only takes one line to define the same setter function:
// Object literal setter with ES6 syntax
var setBirthday = ( name, age ) => ({ name: name, age: age });
console.log( setBirthday( "Jane", 32 ) );
// Object { name: "Jane", age: 32 }
Array Manipulation
You can use arrow functions to manipulate JavaScript arrays as well. For example, let’s have a look at the persons array that includes three object literals, each having a name and age property:
var persons = [
{ name: "John", age: 30 },
{ name: "Jane", age: 32 },
{ name: "James", age: 34 }
];
JavaScript’s built-in map() method lets you call the same function on every element of the array. Using the traditional ES5 notation, you can return the name property of every person in the following way:
// Array manipulation with ES5 syntax
var haveBirthday = persons.map( function(person) {
return person.name;
});
console.log( haveBirthday );
// Array(3) [ "John", "Jane", "James" ]
With the arrow function notation, you can perform the same task in one line:
// Array manipulation with ES6 syntax
var haveBirthday = persons.map( person => person.name );
console.log( haveBirthday );
// Array(3) [ "John", "Jane", "James" ]
When Not to Use Arrow Functions
Although arrow functions have many use cases, they come with some limitations as well. There are some scenarios when you can’t or shouldn’t use the arrow function syntax.
Most importantly, you can’t create constructors with arrow functions. If you use the new keyword together with the fat arrow syntax, the console will throw an error. This happens because JavaScript treats arrow functions in the same way as object methods. As a result, they can’t have their own methods, which would be an essential characteristic of JavaScript objects.
Besides, you can’t use the ES6 syntax to declare object literals and callback functions containing methods that make use of the this keyword, as arrow functions treat this in a different way.
Wrapping Up
Arrow functions provide developers with a useful shorthand to write function expressions in JavaScript. The fat arrow syntax has many use cases, so it has quickly become the favorite ES6 feature of the JavaScript community. If used consistently, the new compact notation can save a lot of time and bandwidth, and improve code readability.
To learn more about JavaScript development, also have a look at our articles about:
- the four different ways to create JS objects,
- how to build a countdown timer in pure JavaScript,
- the most interesting JS frameworks to learn.
To stay informed with the latest web development news, follow us on Twitter, too.