ES6 New Array Methods

Introduction

 
After ES6 was released, I have seen that many developers are still unaware of the recently added functions of the Array object. Therefore, I decided to create this article to spread the information and hope that many will benefit from it.
 

Background

 
This article isn’t about an introduction to JavaScript arrays but more of studying the newly added functions of the Array object. I do suggest that you make a Google search if you are a beginner. Moreover, in my opinion, these added functions do have an aim. And, one of those is to make our lives easier and be productive when working with the Array object. Lastly, if you have a good understanding of arrays, you’ll be comfortable reading this article.
 

ECMAScript 6 Enhanced Arrays

 
As we have mentioned, the ECMAScript 6 (ES6) has added new methods to the global Array object. Therefore, will be discussing the following methods:
  • Array.from()
  • Array.of()
  • copyWithin()
  • fill()
  • find()
  • findIndex()
  • entries()
  • keys()
  • values()
So let’s get started then. I hope you are excited.
 

The Array.from() Method

 
This is a static method that returns a new Array instance from an iterable object. However, you can also pass an “Array-like Object” in the first parameter. If you have no idea about it yet, it will be discussed as part of this section.
 
Syntax
  1. //syntax  
  2. //Array.from(arrayLike[,mapFn[, thisArg]]);  
Parameters
  1. arrayLike – is the reference of an iterable object.
  2. mapFn – is optional, and acts as a callback known as map-function.
  3. thisArg – is optional too, and is the value of this inside the map-function.
Let us see an example below.
  1. let result = Array.from('JavaScript', (val, indx) => `[${indx}]` + "=>" + val.toUpperCase());  
  2.    
  3. console.log(result);  
Output
 
 
As you can see, the example above is easy to follow.
 
Map Function
  • This is the 2nd parameter, if provided, it will act as a mapping callback when invoked. And, it transforms each value from the source to the returned target.
  • This is similar to Array.prototype.map() method.
Now, why not see another example don’t you think? And, why not put the Array.from() inside an Object. Thereby, we can see how the mapping callback function and the 3rd parameter this behaves.
  1. const manager = {  
  2.   isBadManager: true,  
  3.   doBadStuff: function (items) {  
  4.     return Array.from(items, function (val, indx) {  
  5.    
  6.       if (this.isBadManager) {  
  7.         console.log(`${indx + 1}. ${val[0].toUpperCase()}${val.substr(1)}`);  
  8.       }  
  9.     }, this);  
  10.   }  
  11. }  
  12.    
  13. /** 
  14.  * Output: 
  15.  *  1. That's my idea 
  16.  *  2. Micromanage 
  17.  */  
  18. manager.doBadStuff(['that\'s my idea','micromanage']);  
Again, easy to follow example. Now, let’s take it up a notch. And, let’s focus a bit more on the 1st parameter of the Array.map() which is the array-like object (arrayLike).
 

What is an Array-like Object?

 
Usually, you’ll experience some objects in JavaScript that looks like an array, commonly known as “Array-like Object”. Confused? Don’t be. It is an object which has a length property of a non-negative integer and it got some indexed properties.
 
Let us see an example below.
  1. let arrLike1 = {  
  2. length: 3,  
  3. 0: "Jin",  
  4. 1: "Vincent",  
  5. 2: "Necesario"  
  6. };  
That’s it? Yes.
 
Now, let’s look at how we can convert the arrLike1 variable into a real array using Array.from().
  1. let resultArray2 = Array.from(arrLike1);  
  2. console.log(resultArray2);  
  3. //output: ["Jin", "Vincent", "Necesario"]  
NodeList
 
A NodeList is another example of an array-like object. Even I struggled with NodeList I thought it was an array but it is not.
 
NodeList and Arrays are completely different things.
 
OK, so what’s a NodeList? A NodeList object is a collection of DOM nodes that was extracted from the HTML document when using a browser API such as querySelector() and/or querySelectorAll().
 
Now, that we have an idea of what a NodeList is.
 
Let’s try to convert a NodeList to an array with the use of Array.from().
  1. <!-- this is the html file -->  
  2. <body>  
  3.     <div>  
  4.         <p>Hello World 1</p>  
  5.         <p>Hello World 2</p>  
  6.         <p>Hello World 3</p>  
  7.     </div>  
  8. </body>  
  1. /** 
  2.  * Start of NodeList 
  3.  * In this code sample we will see what a NodeList is.  
  4.  * Here are some facts about NodeList.  
  5.  *  
  6.  * 1. NodeList aren't arrays.  
  7.  * 2. NodeList does have a length property 
  8.  * 3. NodeList does have indexed property 
  9.  * 4. Therefore, we can conclued that a NodeList does looks like 
  10.  *    an Array-like object. 
  11.  * 5. We can convert NodeList into an array with the use of Array.from() 
  12.  */  
  13. window.addEventListener("DOMContentLoaded"function (event) {   
  14.   
  15.   let elements = document.querySelectorAll("div p");  
  16.   
  17.   console.log(elements); //output: NodeList(3) [p, p, p]  
  18.   
  19.   //this proves that NodeList does have a length property  
  20.   console.log(elements.length) //output: 3  
  21.   
  22.   console.log(typeof (elements)); //output: object  
  23.     
  24.   //this proves that the return of querySelectorAll method is a NodeList  
  25.   console.log(elements instanceof NodeList); //output: true  
  26.   
  27.   //this proves that NodeList aren't arrays  
  28.   console.log(elements instanceof Array); //output: false  
  29.   
  30.   let arrayParagraphs = Array.from(elements);  
  31.   
  32.   console.log(arrayParagraphs); //output: Array(3)  
  33.   
  34. });  
  35.  /** 
  36.   * End of NodeList 
  37.   */  
Output
 
 
Now, that we are familiar with the array-like object and we have seen how to convert into a real array.
 
The next concept we need to understand is how to avoid empty slots.
 

Avoiding Empty Slots

 
Empty slots? What are they?
 
Basically, when you create an array to a certain length without specifying the values per index you’ll have an empty index also known as an empty slot.
 
Let us see an example below.
  1. const arrWithEmptySlots = [];  
  2. arrWithEmptySlots.length = 5;  
  3. arrWithEmptySlots[0] = "Jin";  
  4.    
  5. //output ["Jin", empty × 4]  
  6. console.log(arrWithEmptySlots);  
Output
 
How can I check for empty slots?
 
We can use the in operator to check if the array has a key. Moreover, it returns a boolean value, false for empty slots but true for slots with value, including the undefined value.
 
Let us see an example below.
  1. const arrWithEmptySlots = [];  
  2. arrWithEmptySlots.length = 3;  
  3. arrWithEmptySlots[0] = undefined;  
  4. arrWithEmptySlots[1] = "Jin";  
  5.    
  6. console.log(0 in arrWithEmptySlots);//true  
  7. console.log(1 in arrWithEmptySlots);//true  
  8. console.log(2 in arrWithEmptySlots);//false  
  9. console.log(3 in arrWithEmptySlots);//false  
  10.    
  11. /** 
  12.  * output: 
  13.  * 0 
  14.  * 1 
  15.  */  
  16. for (let slot in arrWithEmptySlots) {  
  17.   console.log(slot);  
  18. }  
What’s this empty slot got to do with the Array.from() method?
 
If you wanted to produce an array initialized to a certain length without empty slots, Array.from() solves that.
 
Let us see an example below.
  1. const arrayWithEmptySlots_2 = [];  
  2. arrayWithEmptySlots_2.length = 5;  
  3.    
  4. const results = Array.from(arrayWithEmptySlots_2);  
  5.    
  6. //output: [undefined, undefined, undefined, undefined, undefined]  
  7. console.log(results);  
Before we move to the next section.
 
We can then conclude that Array.from() not only creates a new Array instance from an iterable object.
 
It also accepts an “Array-like Object” that will be converted into a real array and helps us to avoid empty slots.
 

The Array.of() Method

 
Mostly, everyone understands that an Array constructor is utilized to create an Array-object. Moreover, Array.of() method comes in as an alternative to the Array constructor and we are going to see why, in this section.
 
Syntax
  1. //syntax  
  2. //Array.of([]);  
Parameters
  1. [] – elements used to create the array.
Let us see some examples below.
 
Create a new Array constructor and pass more than one argument.
  1. let cars = new Array("Toyota""Mitsubishi""Nissan""Honda");  
  2.    
  3. //output: 4  
  4. console.log(cars.length);   
  5. //output: Toyota Mitsubishi Nissan Honda  
  6. console.log(...cars);   
  7.    
  8. let customers = new Array({ name: "Jin" }, { name: "Vincent" }, { name: "Necesario" });  
  9.    
  10. //output: 3  
  11. console.log(customers.length);   
  12. //output: {name: "Jin"} {name: "Vincent"} {name: "Necesario"}  
  13. console.log(...customers);   
  14.    
  15. let luckyNumbers = new Array(23, 29, 32);  
  16.    
  17. //output: 3  
  18. console.log(luckyNumbers.length);  
  19. //output: 23 29 32  
  20. console.log(...luckyNumbers);  
Create a new Array constructor and pass one argument. And, let us see the glitch.
  1. let car = new Array("Toyota");  
  2. //still works.  
  3. console.log(car);   
  4.    
  5. let customer = new Array({name: "Jin"})  
  6.  //still works.  
  7. console.log(customer);  
  8.    
  9. let luckyNumber = new Array(23);  
  10. //glitch  
  11. //output: 23  
  12. //23 in length????  
  13. console.log(luckyNumber.length);   
  14.    
  15. //another glitch  
  16. //output:  [empty × 23]  
  17. console.log(luckyNumber);   
A Small Glitch?
 
Did you spot the difference? Let’s take for instance the luckyNumber variable, it resulted differently compare to the variables car and customer.
 
Remember that when you have passed one argument with a number value.
 
It is creating an empty array with a length property equal to the number and produces empty slots based on the length property.
 
Is this a glitch? Maybe yes or maybe no. In order for us to avoid this issue, we can use the Array.of() method.
 
Let us see an example below. 
  1. let superLuckyNumber = Array.of(23);  
  2. console.log(superLuckyNumber); //output: [23]  
Therefore the Array.of() method was introduced to resolve the issue.
 
Let me know your thoughts in the comment section. Thanks in advance.
 

The copyWithin() Method

 
The copyWithin() method is used to copy the sequence of values of the array to a different position in the array.
 
Syntax
  1. //syntax  
  2. //[].copyWithin(target, start, end);  
Parameters
  1. target – is the index where to copy elements.
  2. start – is optional, and this is the index position where to start copying from.
  3. end – is optional, and this is the index where to actually end copying elements.
If start index is negative, it’s treated as length of array plus start-index ([].length + start). Same as with end index ([].length + end).
 
Let us see an example below.
  1. let presidents1 = ["Donald Trump""Barack Obama""George Bush""Bill Clinton"];  
  2. let presidents2 = ["George H. W. Bush""Ronald Reagan""Jimmy Carter""General Ford"];  
  3. //let's copy to index 0 from index 1  
  4. //let's replace Donald Trump with Barack Obama  
  5. //output: ["Barack Obama", "George Bush", "Bill Clinton", "Bill Clinton"]  
  6. console.log(presidents1.copyWithin(0, 1));  
  7. //let's copy to index 1 from index 2  
  8. //let's replace Ronald Reagan with Jimmy Carter up to 3rd index.  
  9. //Up to 2nd index only excluding 3rd index.  
  10. //output: ["George H. W. Bush", "Jimmy Carter", "Jimmy Carter", "General Ford"]  
  11. console.log(presidents2.copyWithin(1, 2, 3));  
Easy to follow isn’t? Let’s move to the next section.
 

The fill() Method

 
The fill method actually fills (entirely or partially) all the elements of the array from the start index to the end index with the given value. Moreover, the start and end index are optional; therefore if they are not provided then the entire array is filled by the value you passed.
 
Syntax
  1. //syntax  
  2. //[].fill(value, start, end);  
Parameters
  1. value – the value to fill the array.
  2. start – optional, and is the start-index.
  3. end – optional, and is the end-index.
If you have seen the issue of the Array constructor. Likewise, we can use this method to set the values for all the empty slots of the array.
 
You can do this as long as your target is to initialize an array with defined length and with no empty slots.
 
Let us see an example below.
  1. let arryLenOf5 = new Array(5).fill(undefined);  
  2. //output: (5)[undefined, undefined, undefined, undefined, undefined]  
  3. console.log(arryLenOf5);  
  4. let arryLenOf3 = new Array(3).fill(0);  
  5. //output: (3) [0, 0, 0]  
  6. console.log(arryLenOf3);  
Let us see some examples again.
  1. //fills the entire array  
  2. console.log([29, 23, 5, 26, 16, 21].fill(29));  
  3. //output: [29, 29, 29, 29, 29, 29]  
  4. //fills the entire array starting at index 1  
  5. console.log([29, 23, 5, 26, 16, 21].fill(30, 1));  
  6. //output: [29, 30, 30, 30, 30, 30]  
  7. //fills the entire array starting at index 1 and ends at 5th position.  
  8. console.log([29, 23, 5, 26, 16, 21].fill(31, 2, 5));  
  9. //output: [29, 23, 31, 31, 31, 21]  
If start index is negative, it’s treated as length of array plus start-index ([].length + start). Same as with end index ([].length + end).
  1. //fills the entire array starting at index ([].length -2) = 4th index.  
  2. console.log([29, 23, 5, 26, 16, 21].fill(31, -2));  
  3. //output: [29, 23, 5, 26, 31, 31]  
  4. //fills the entire array starting at [1] index ends to ([].length -2) = 4th position.  
  5. console.log([29, 23, 5, 26, 16, 21].fill(31, 1, -2));  
  6. //output: [29, 31, 31, 31, 16, 21]  
Easy to follow isn’t? Let’s move to the next section.
 

The find() Method

 
Before we go in-depth with the find() method will step back a bit. And answer: “What it does really resolves?”.
 
Syntax
  1. //syntax  
  2. //[].find(callback(element,index,array), thisArg);  
Parameters
  1. callback – a callback function that executes on each value in the array.
  2. thisArg – is optional, Object to use as this inside the callback.

The indexOf Method

 
Usually, the first thing that comes to mind when searching for a value in an array has been the use of the indexOf() method.
 
Let’s see an example below.
  1. let nums = [9, 8, 7, 6, 5, 4, 3, 2, 1];  
  2. console.log(nums.indexOf(9)); //output: 0;  
  3. console.log((nums.indexOf(7) !== -1)); //output: true  
  4. console.log((nums.indexOf("9") == 0)); //output: false  
  5. console.log((nums.indexOf("Jin Vincent Necesario") !== -1)); //output: false  
However, sometimes programmers forgets that this method requires a strict comparison. In my opinion, that’s why they (programmers) uses the some() method.
 
The some() Method
 
This method works by invoking a function callback for each element until one returns a true or truthy value, and finally, it stops.
 
The benefit is you have control over the comparison of values not unlike the indexOf() method.
 
Let us see an example below.
  1. let nums = [9, 8, 7, 6, 5, 4, 3, 2, 1];  
  2. console.log(nums.some((num) => num == "9")); //output: true  
  3. console.log(nums.some((num) => num === "9")); //output: false  
Now, the drawback of the some() method is you can only get the boolean values true or false, if a suitably matched value was found, but not what the actual value matched.
 

What does find() Method resolve?

 
The find() method resolves that issue. It works like the some() method, except once the callback returns its value, the actual array value is returned.
 
Therefore, the find() method returns an array element. Only, if it satisfies the provided expression passed to the callback function. Otherwise, it returns undefined.
 
Let’s see an example below.
  1. let nums = [9, 8, 7, 6, 5, 4, 3, 2, 1];  
  2. console.log(nums.find((num) => num == "9")); //output: 9  
  3. console.log(nums.find((num) => num === "9"));//output: undefined  
Why not another example with the complete parameters?
  1. let num = 5;  
  2. let nums = [9, 8, 7, 6, 5, 4, 3, 2, 1];  
  3. let result = nums.find(function (value, index, array) {  
  4. //just shows the values to the console window.  
  5. console.log(`The num[${index}] is equal to ${value} ${this}`);  
  6. return value === parseInt(this);  
  7. }, num);  
  8. console.log(result); //output: 5  

The findIndex() Method

 
This is almost similar to the find() method. However, it returns the index of the array element instead of the element itself.
 
Syntax 
  1. //syntax  
  2. //[].findIndex(callback(element,index,array), thisArg);  
Parameters
  1. callback – a callback function that executes on each value in the array until the function returns true. Otherwise, undefined, which indicates that element wasn’t found.
  2. thisArg – is optional.
Going back to the indexOf() method, we have seen that’s there no control over its matching logic. Thus, findIndex() saves the day.
 
Let’s see an example below.
  1. let num = 5;  
  2. let nums = [9, 8, 7, 6, 5, 4, 3, 2, 1];  
  3. let result = nums.findIndex(function (value, index, array) {  
  4. //just shows the values to the console window.  
  5. console.log(`The num[${index}] is equal to ${value} ${this}`);  
  6. return value === parseInt(this);  
  7. }, num);  
  8. console.log(result); //output: 4  
Now, that we have a good background on the find() method and the similarities of find() and findIndex().
 
Let’s have another example, a customized search.
  1. const houses = [  
  2. { length: 22, width: 288, measurement: 'ft' },  
  3. { length: 182, width: 532, measurement: 'ft' },  
  4. { length: 12, width: 152, measurement: 'ft' },  
  5. { length: 20, width: 30, measurement: 'ft' },  
  6. { length: 12, width: 152, measurement: 'ft' }];  
  7. let indexResult = houses.findIndex((house) => (house.length * house.width) === 600);  
  8. console.log(indexResult); //output: 3  
When To Use find() and findIndex() Method?
  • Don’t treat the findIndex() method just like on how we use the indexOf() method for comparison because we have the some() method that returns the boolean value we need.
  • Don’t use the findIndex() method to get the matched value because that’s what the find() method for.
  • Use the indexOf() method if you need a strict match.
  • Use the findIndex() if you need the index of a more customized match.

The entries() Method

 
This method returns an iterable object. Moreover, the actual returned object is an Array Iterator that contains key/value pairs for each index of the array.
 
Syntax
  1. //syntax  
  2. //[].entries();  
Let us see an example below.
  1. let fruits = ['mango''apple''dragon fruit'];  
  2. //output: returns Array Iterator {}  
  3. console.log(fruits.entries());  
  4. /* 
  5. Let us show the [key, value] pair 
  6. */  
  7. let fruitEntries = fruits.entries();  
  8. /* 
  9. Output: 
  10. [0, "mango"] 
  11. [1, "apple"] 
  12. [2, "dragon fruit"] 
  13. */  
  14. for (let current of fruitEntries){  
  15. console.log(current);  
  16. }  
  17. /*let us show the index and element of the fruits array 
  18. Output: 
  19. 0 "mango" 
  20. 1 "apple" 
  21. 2 "dragon fruit" 
  22. */  
  23. for(let [index, element] of fruits.entries()){  
  24. console.log(index, element);  
  25. }  

The keys() Method

 
This method is similar to the entries() method. However, the object returned contains the keys for each index in the array.
 
Syntax
  1. //syntax  
  2. //[].keys();  
Let us see an example below.
  1. let fruits = ['mango''apple''dragon fruit'];  
  2. //output: Array Iterator {}  
  3. console.log(fruits.keys());  
  4. let fruitKeys = fruits.keys();  
  5. //output: 0 1 2  
  6. console.log(...fruitKeys);  

The values() Method

 
This method behaves similarly to [].keys() and [].entries(). However, the difference, this method returns the value of each key in the array.
 
Syntax
  1. //syntax   
  2. [].values();  
Let us see an example. 
  1. let fruits = ['mango''apple''dragon fruit'];  
  2. //output: Array Iterator {}  
  3. console.log(fruits.values());  
  4. let fruitKeys = fruits.values();  
  5. //output: "mango" "apple" "dragon fruit"  
  6. console.log(...fruitKeys);  

Summary

 
In this post, we have learned the new Array-object methods of the JavaScript(ES6) language. Moreover, we have tackled how these methods work, why it’s added, and what issue/issues it resolves. Overall, we have seen the history and benefits of these methods. I hope you have enjoyed reading this article, as much as I have enjoyed writing it. Stay tuned for more. This article was originally written and posted here. Until next time, happy programming!