JavaScript is an ever-evolving programming language, with yearly EcmaScript versions debuting new features every year. That makes it difficult to keep up with all the changes that are being made to the language so I thought I would write a short post of 5 features that you could use to improve your own code.
1. JavaScript string padding
The first JavaScript feature I wanted to talk about is the result of an incident that happened back in 2016 in the JavaScript ecosystem.
The incident involved a JavaScript package called left-pad which was published to NPM. The purpose of the package was to pad a string with extra characters, and while simple in nature the package was a dependency of thousands of JavaScript projects worldwide.
The incident happened when it was removed from NPM and as it was depended on by many packages it caused a domino effect breaking software builds all over the world.
While NPM fixed the issue, it became evident to the folk at TC39 that a lot of people were preferring to use a library to pad strings than write the code themselves thus as part of ES2017 they introduced .padStart() and .padEnd().
To add 0’s to the beginning of a string we would use .padStart(), passing the target length for the string and the string to pad the current string with. In the below example I am padding the string "1" so that it has a length of "4".
let str = "1";
str = str.padStart(4,0);
console.log(str) // output is 0001
Alternatively, we might want to pad the end of our string and for this, we can use .padEnd()
.
Similar to the example above, we pass both the target length for the string and the string to pad the current string with to .padEnd()
. In the below example I am padding the string “1” so that it has a length of “4”. This time however it will add the padding to the end.
let str = "1";
str = str.padEnd(4,0);
console.log(str) // result is 1000
2. Spread operator
The Spread operator isn’t the newest and shiniest of JavaScript features, arriving back in 2015 as part of the ES2015 specification however some of its use cases are often overlooked.
The first use case of the spread operator is to add the items from one array to another array. In the example below I have an array with 3 fruit however I want a second array which has the fourth fruit so I use the spread operator to copy the original fruit, and add the fourth fruit.
const arr1 = ["Apple", "Orange", "Pear"]
const arr2 = [...arr1, "Banana"]
console.log(arr2) // ["Apple", "Orange", "Pear", "Banana"]
We can do a similar thing with objects, however with the added benefit that we can override values in the original object.
const personA = {
name: "Jonathan",
age: 21,
}
const personB = {
...personA,
name: 'Charlie'
}
console.log(personB) // {name: "Charlie", age: 21}
3. Rest parameter
Following on from the Spread operator, we have the Rest parameter, which is kind of like its opposite. The rest syntax collects multiple elements and “condenses” them into a single element.
A good use case for the rest parameter is to group the remaining elements of an array when it is being destructured. In the below example we have some fruits which we destructure so the apple is on its own, with the remaining fruit are left in a fruits array.
const [apple, ...fruits] = ["apple", "orange", "pear"];
console.log(apple); // output is "apple"
console.log(fruits); // output is ["orange", "pear"]
4. Array.prototype.includes
The next feature I want to talk about is Array.prototype.includes, this feature allows you to find if an array contains an item.
Prior to Array.prototype.includes, this would have been achieved by looping through the array and setting a variable to true if the item is found, see below:
const fruits = ["Dragonfruit", "Kiwi", "Mango", "Pear", "Starfruit"];
let found = false;
fruits.forEach(function(fruit) {
if (fruit === 'Kiwi') {
found = true;
}
});
console.log(found); // Outputs `true`
Now, with Array.prototype.includes, we can reduce this significantly to the following.
const fruits = ["Dragonfruit", "Kiwi", "Mango", "Pear", "Starfruit"];
const found = fruits.includes("Kiwi");
console.log(found); // Outputs `true`
Note: as developers, we don’t need to worry about how this search is now implemented so the browsers have the opportunity to optimise this behaviour themselves.
5. Optional Chaining
The fifth and final feature I want to talk about is Optional Chaining.
Optional Chaining allows us to attempt to retrieve data nested deeply within an object without having to handle the situation where the data might not exist.
Lets take a look at the below example, in this we are defining Jonathan with some meta data.
const jonathan = {
name: "Jonathan",
meta: {
age: 21
}
}
const age = jonathan.meta.age;
const gender = jonathan.other.gender; // Will throw error
console.log(age);
console.log(gender);
If we run this code it results in an error as the other section of the object does not exist.
With optional chaining we can prevent this error by saying, don’t go further in the objects tree if a property does not exist. I updated the code below with optional chaining.
const jonathan = {
name: "Jonathan",
meta: {
age: 21
}
}
const age = jonathan?.meta?.age;
const gender = Jonathan?.other?.gender;
console.log(age); // outputs 21
console.log(gender); // outputs "undefined"
If we run this now, there will no longer be an error and the gender will simply be undefined which we can handle separately.
Wrapping up
JavaScript is rapidly advancing faster than it has ever before, with yearly updates the language keeping it fresh it's very easy to forget about all the cool things we can do with features that are even just a couple of years old.
In my own experience, writing this post actually led to me learning more about each of the features I talked about. Helping me to reinforce my own knowledge along the way.
Thank you for taking the time to read, if you want to read similar posts please follow me on Medium.
Top comments (0)