JavaScript Function Arguments ES6 Style!

Monday May 22nd 2017 by Rob Gravelle
Share:

In the ECMAScript 6 (ES6) spec, function arguments were enhanced with default values, rest parameters, and the spread operator. Rob Gravelle describes each of the new features and presents examples that illustrate their usage.

TC39 (Ecma Technical Committee 39), the committee that evolves JavaScript, released the ECMAScript 6 (ES6) spec in June of 2015. It contains a ton of new features, including Arrows, Tail Calls, Object Literals, and Destructuring Assignments. One area that received a lot of updates was function arguments. These were enhanced with default values, rest parameters, and the spread operator. In today's tutorial, I'll go over each of these features and present examples that illustrate usage.

Using ES6 Syntax

Since 2015, browser vendors' adoption of ES6 has been somewhat spotty. Hence, most browsers only support some ES6 features: the new Microsoft Edge browser has over eighty percent ES6 support, and FF/Chrome are around 50-60%. Ideally, you would want to test for specific features and employ some sort of shiv if a feature is not supported. Unfortunately, Modernizr-style feature testing for syntax doesn't work because the ES6 syntax fails JS compilation in pre-ES6 compliant browsers before it runs, so try...catch blocks are useless.

For that reason, your best bet is to use a transpilation tool. These are a special kind of preprocessor — the likes of which include CoffeeScript (JavaScript), Sass (CSS), and HAML (HTML) — that compiles ES6 code into ES5 code, so that it will run on non- or semi- compliant browsers. The three most popular ones right now are Traceur, Babel, and TypeScript. I personally recommend Babel because supports the greatest number of ES6 features. Moreover, it also supports JSX by React, which is a powerful UI framework, and enjoys a vibrant and growing community of development and support.

Using Babel

BabelJS is of course named after the Tower of Babel, from the book of Genesis, which was a Biblical account of the origin of our many languages. The story goes that, several generations after the Great Flood, a united humanity decided to build a city and a tower "tall enough to reach heaven". This monument to ambition angered God, so he punished mankind by confounding their speech, so that they could no longer understand each other, and scattered them all over the world.

Thankfully, we now have automated translation tools like Babelfish to help people communicate. Unlike BabelJS, Babelfish is named after the fictional Babel fish of Hitchhiker's Guide to the Galaxy. It's a small, yellow, leech-like fish that, when inserted into a person's ear, acts as a universal translator that can cross the language divide between any species.

There are lots of ways to use BabelJS, but probably the easiest is to include a reference to the hosted stand-alone version in your page. Then, assign your scripts that use ES6 syntax a type of "text/babel". That will prevent your browser's JS engine from trying to execute the code within the script tags as well as tell BabelJS which ones to process:

<!-- Load Babel -->
<script src="https://unpkg.com/babel-standalone@6/babel.min.js"></script>
<!-- Your custom script here -->
<script type="text/babel">
  const getMessage = () => "Hello World";
  document.getElementById('output').innerHTML = getMessage();
</script>

Default Parameters

Let's begin by defining what Default Parameters are: default function parameters allow parameters to be initialized with default values if no value or undefined is explicitly passed.

In ES5, you had to check each parameter inside the function using either a falsy or explicit test against the "undefined" constant. ES6 replaces these clunky checks with direct parameter assigning right in the signature:

// ES5
function add(x, y) {
  if (x === undefined) x = 0;
  y = y || 0;
  return x + y;
}
 
// ES6
function add(x=0, y=0) {
  return x + y;
}

The values may be of any acceptable JavaScript type, including numbers, strings, dates, arrays, and even custom objects.

Variable Number of Parameters

One of the great things about JavaScript is its support for variable parameter lengths. That's where you have a function that can accept a different number of parameters on every invocation. For instance, why can't our add() function above accept more than two numbers? We can by accessing the arguments property:

// ES5
function add(x, y) {
  if (x === undefined) x = 0;
  y = y || 0;
  var sum = x + y;
  
  //initialize i to the optional 3rd argument
  for(var i=2; i<arguments.length; i++) sum += arguments[i];
  
  return sum;
}

ES6's Rest Argument aggregates the remaining arguments into a single parameter of variable length. It does not replace the arguments property, but offers a couple of additional features:

  1. the rest parameters is a real Array, and hence wields methods like sort(), map(), forEach(), and pop()
  2. applies only the parameters that haven't been named within the function signature

Here is the add() function again with a rest parameter:


// ES6
function add(x=0, y=0, ...a) {
  let sum = x + y;
  a.forEach(a => sum += a);
  
  return sum;
}

The application of the forEach() function also benefits from the more succinct ES6 syntax.

Spread Operator

The Spread operator looks a lot like the Rest parameter because of the three dots, but it is employed outside of a function signature. It's thusly named because spreads of elements of an iterable collection (like an array or even a string) into both literal elements or individual function parameters, depending on the context:


//For function calls:
let numbers = [1,2,3];
add(...numbers);  //like calling add(1,2,3)

//For array literals:
[...numbers, 4, 5, 6];  //creates [1,2,3,4,5,6]

It replaces Function.apply() so that:

function add(x,y) { }
var numbers = [1, 2, 3];
add.apply(undefined, numbers);

This can be written as follows with spread syntax:

function add(x=0, y=0, ...a) { }
let numbers = [0, 1, 2];
add(...numbers);

Here's a demo of today's ES6 code snippets.



Rob Gravelle

Rob Gravelle resides in Ottawa, Canada, and has built Web applications for numerous businesses and government agencies. Email Rob.

Rob's alter-ego, "Blackjacques", is an accomplished guitar player, that has released several CDs and cover songs. His band, Ivory Knight, was rated as one of Canada's top hard rock and metal groups by Brave Words magazine (issue #92) and reached the #1 spot in the National Heavy Metal charts on ReverbNation.com.

Share:
Home
Mobile Site | Full Site
Copyright 2017 © QuinStreet Inc. All Rights Reserved