5 useful tips about the JavaScript array sort method
JavaScript arrays
are an ordered collection that can hold data of any type. Arrays are created with square brackets [...] and allow duplicate elements. In JavaScript, we can sort the elements of an array with the built-in method called, sort()
.
In this article, we will learn about the sort()
method with 5 important tips(or information). Hope you find them useful.
1. The default array.sort() is for string type
The sort()
method sorts the array elements and returns the sorted array.
let artists = [
'John White Abbott',
'Leonardo da Vinci',
'Charles Aubry',
'Anna Atkins',
'Barent Avercamp'
];
let sorted = artists.sort();
console.log('Sort the artist names', sorted);
Output,
Sort the artist names
[
"Anna Atkins",
"Barent Avercamp",
"Charles Aubry",
"John White Abbott",
"Leonardo da Vinci"
]
Please note, the sort()
method actually mutates the original array and both the original and sorted arrays are the same references.
console.log(artists === sorted); // returns true
Alright, an important point to note here is,
With the
sort()
method, the default sort order isascending
, and elements are converted into strings. Hence the defaultsort()
method is not enough to sort arrays with different data type elements.
How about descending sorting order?
The default sort()
method sorts in ascending order. How do we perform a sort in descending order? Welcome, compare function
. A compare function
helps elements to sort in an order according to its return value. Let us see it with an example,
// A compare function
function (a, b) {
if (a > b) {
return -1;
}
if (a < b) {
return 1;
}
// a must be equal to b
return 0;
}
The above compare function helps to compare each of the elements in an array to perform a descending sort. Of course, the same function can be written in much simpler way as,
function (a,b) {
return a === b ? 0 : a > b ? -1 : 1;
}
So now, let us sort the artists
array in the descending order,
artists.sort(function (a, b) {
return a === b ? 0 : a > b ? -1 : 1;
});
console.log('Sort the artist names(Descending)', artists);
Output,
Sort the artist names(Descending)
[
"Leonardo da Vinci",
"John White Abbott",
"Charles Aubry",
"Barent Avercamp",
"Anna Atkins"
]
How about sorting numbers?
The same philosophy applies. The default sort()
function can not do it correctly. See this,
let ages = [2, 1000, 10, 3, 23, 12, 30, 21];
ages.sort();
console.log(ages);
Output,
[10, 1000, 12, 2, 21, 23, 3, 30]
Weird right? Yeah because with the default sort()
, elements are converted to strings and compared in UTF-16 code units order. Hence the converted "12" comes before the converted "2".
We need a compare function
for rescue here again. An ascending order sort can be done as,
ages.sort(function(a,b) {return a-b});
console.log(ages);
Note, the compare function passed to the sort()
method. The compare function subtracts a from b and the result will be either of a positive number, negative number, or zero.
If you are using the ES6
coding style, you can write it using the arrow
function as,
ages.sort((a,b) => a-b);
Output,
[2, 3, 10, 12, 21, 23, 30, 1000]
A descending number sort is an easy change, instead of the a-b
, return b-a
from the compare function.
ages.sort(function(a,b) {return b-a})
console.log(ages);
Output,
[1000, 30, 23, 21, 12, 10, 3, 2]
2. The array.reverse() is a force fit for sorting
The array.reverse()
is another useful array method to order the elements in a reverse way.
let arr = ['bob', 'anna', 'elsa', 'marlon'];
console.log(arr.reverse());
Output,
["marlon", "elsa", "anna", "bob"]
As you see, the array elements are in reverse order now. This is good but, we often use the reverse()
method for sorting.
let arr = ['bob', 'anna', 'elsa', 'marlon'];
let sorted = arr.sort(); // Ascending
let reversed = sorted.reverse(); // Descending
console.log(reversed);
Output,
["marlon", "elsa", "bob", "anna"]
It works but, may lead to an unexpected result as the reverse()
is not meant for an order sorting, it is just for reversing. Please use the proper compare function for your sorting needs.
3. The non-ASCII character sorting is easy
In your application, you may encounter the strings which are non-English and represented by the non-ASCII characters. Use the string localeCompare()
method in your compare function to sort them.
let items = ['communiqué', 'zèbre', 'adieu', 'éclair'];
items.sort();
console.log('Without localeCompare', items);
items.sort((a,b) => a.localeCompare(b));
console.log('With localeCompare', items);
Output,
Without localeCompare
[
"adieu",
"communiqué",
"zèbre",
"éclair"
]
With localeCompare
[
"adieu",
"communiqué",
"éclair",
"zèbre"
]
4. Sorting an object array == Sorting on value types
In JavaScript, objects
are used to store multiple values as a complex data structure.
An object is created with curly braces {…}
and a list of properties
. A property
is a key-value
pair where the key
must be a string and the value
can be of any type.
Sorting an object is mostly about sorting based on property values. As the values can be of any type, let us understand various sorting with examples,
A user
object,
let users = [
{'name': 'Joe', 'address': 'Huston', 'dob':'February 9, 1991', 'income': 87654},
{'name': 'Bob', 'address': 'London', 'dob':'July 1, 1986', 'income': 47974},
{'name': 'Carl', 'address': 'Bangalore', 'dob':'December 25, 1982', 'income': 97351},
{'name': 'Amanda', 'address': 'Lagos', 'dob':'March 19, 2001', 'income': 57753},
];
Sort by name
Use the compare function to compare the names of each object in the array.
users.sort(function(a, b) {
let left = a.name;
let right = b.name;
return left === right ? 0 : left > right ? 1 : -1;
});
console.table(users);
Output,
You know, what to do for a descending sort, right? Yeah, a bit of change in the compare function as shown earlier.
Sort by income
Income values are numbers. We know what to do here. We are going to compare the income values of the objects.
users.sort((a,b) => (a.income - b.income));
console.table(users);
Output,
Sort by date of birth(dob)
The user has a date of birth(dob property) which is a string. Well, we can not sort them like string, right? We need to sort them like dates. For a change, we are doing a descending order sort here means, the young person will be at the top.
users.sort((a,b) => (new Date(b.dob) - new Date(a.dob)));
console.table(users);
Output,
5. You may need the case insensitive sorting
You may have to deal with array elements of different cases(capital and small). The default sort()
function may not help. Here is an array with elements of mixed cases.
let names = ['Bob', 'bakshi', 'adam', 'Maya', 'carl'];
names.sort();
console.log(names);
Output,
["Bob", "Maya", "adam", "bakshi", "carl"]
The above output is actually right as the comparison happens in the UTF-16 code
units order. However, you may want it in the following order,
"adam", "bakshi", "Bob", "carl", "Maya"
Use the compare function and compare the elements with the toUpperCase()
to do a case insensitive comparison.
names.sort(function (a, b) {
let left = a.toUpperCase();
let right = b.toUpperCase();
return (left === right) ? 0 : left > right ? 1 : -1;
});
console.log(names);
Output,
["adam", "bakshi", "Bob", "carl", "Maya"]
In Summary
The array sort()
is easy to use. A comparison function is required in most of the cases.
In this article, we have discussed 5 key points,
- The default
array.sort()
method sorts the array elements in the ascending order by converting them to strings. - Do not use
array.reverse()
for sorting. It may lead to unexpected results. - We can use the method
localeCompare()
to sort thenon-ASCII
characters. - Sorting an array of objects many need sorting on various
data types
. Case insensitive
sorting may be required in some cases.
Hope you find it useful. All the source code used in this article are here in my GitHub repo. Feel free to follow as I keep updating them with code examples.
If it was useful to you, please Like/Share so that, it reaches others as well. Please hit the Subscribe button at the top of the page to get an email notification on my latest posts.
You can @ me on Twitter (@tapasadhikary) with comments, or feel free to follow me.