DEV Community

Cover image for Understanding Array.sort compareFn
SeongKuk Han
SeongKuk Han

Posted on

Understanding Array.sort compareFn

Understanding Array.sort compareFn

With compareFn which is an option of sort, you can sort elements in an order that you want.

compareFn: Specifies a function that defines the sort order. If omitted, the array elements are converted to strings, then sorted according to each character's Unicode code point value.

In the documentation, in order to use compareFn, you should read it thoroughly

  • A comparator conforming to the constraints above will always be able to return all of 1, 0, and -1, or consistently return 0. For example, if a comparator only returns 1 and 0, or only returns 0 and -1, it will not be able to sort reliably because anti-symmetry is broken. A comparator that always returns 0 will cause the array to not be changed at all, but is reliable nonetheless.

Let's begin with a number array.

const arr = [4, 3, 1, 5, 2];

arr.sort((a, b) => a - b);

console.log(arr);

arr.sort((a, b) => b - a);

console.log(arr);
Enter fullscreen mode Exit fullscreen mode
[ 1, 2, 3, 4, 5 ]
[ 5, 4, 3, 2, 1 ]
Enter fullscreen mode Exit fullscreen mode

I sorted it in ascending and reversed.

What do value a and b have?
Let's print it out.

const arr = [4, 3, 1, 5, 2];

arr.sort((a, b) => {
  console.log(a, b);
  return a - b;
});
Enter fullscreen mode Exit fullscreen mode
3 4
1 3
5 1
5 3
5 4
2 4
2 3
2 1
Enter fullscreen mode Exit fullscreen mode

In the result, only one thing we should know that a element is next element of b element.

Let's say. We want to place a specific value 3 at the first position.

We can do like this.

const arr = [4, 3, 1, 5, 2];

arr.sort((a, b) => {
  if (a === 3) return -1;
  else if (b === 3) return 0;

  return a - b;
});

console.log(arr);
Enter fullscreen mode Exit fullscreen mode
[ 3, 1, 2, 4, 5 ]
Enter fullscreen mode Exit fullscreen mode

We are also be able to sort an object array.

const objArr = [
  {
    name: "Bob",
    age: 30,
  },
  {
    name: "Delta",
    age: 23,
  },
  {
    name: "Charlie",
    age: 25,
  },
  {
    name: "Echo",
    age: 29,
  },
  {
    name: "Charlie",
    age: 25,
  },
  {
    name: "Alice",
    age: 20,
  },
];
Enter fullscreen mode Exit fullscreen mode

Let's try to sort it by age in ascending.

const objArr = [
  {
    name: "Bob",
    age: 30,
  },
  {
    name: "Delta",
    age: 23,
  },
  {
    name: "Charlie",
    age: 25,
  },
  {
    name: "Echo",
    age: 29,
  },
  {
    name: "Alice",
    age: 20,
  },
];

objArr.sort((a, b) => {
  return a.age - b.age;
});

console.log(objArr);
Enter fullscreen mode Exit fullscreen mode
[
  { name: 'Alice', age: 20 },
  { name: 'Delta', age: 23 },
  { name: 'Charlie', age: 25 },
  { name: 'Echo', age: 29 },
  { name: 'Bob', age: 30 }
]
Enter fullscreen mode Exit fullscreen mode

We can sort it by string using String.localeCompare.

  • The localeCompare() method returns a number indicating whether a reference string comes before, or after, or is the same as the given string in sort order.

You can check out more details about the function in the document.

For the first, let's see results of the function.

console.log("a".localeCompare("a"));
console.log("a".localeCompare("b"));
console.log("b".localeCompare("a"));
Enter fullscreen mode Exit fullscreen mode
0
-1
1
Enter fullscreen mode Exit fullscreen mode

When the parameter comes after the string, it returns -1.
In other words, when the string comes before the parameter, it returns -1.

Just pick two names that has to be switched.
I picked Charlie and Delta.
To switch these, we have to return -1..
The element that has Charlie comes after the element that has Delta, right?

So, a will be an element that has Charlie and b will be an element that has Delta.

"Charlie".localeCompare("Delta");
Enter fullscreen mode Exit fullscreen mode

It will return -1.

It means

a.name.localeCompare(b.name);
Enter fullscreen mode Exit fullscreen mode

This will be our compareFn function.
Okay, let's sort the object array by name.

const objArr = [
  {
    name: "Bob",
    age: 30,
  },
  {
    name: "Delta",
    age: 23,
  },
  {
    name: "Charlie",
    age: 25,
  },
  {
    name: "Echo",
    age: 29,
  },
  {
    name: "Alice",
    age: 20,
  },
];

objArr.sort((a, b) => {
  return a.name.localeCompare(b.name);
});

console.log(objArr);
Enter fullscreen mode Exit fullscreen mode
[
  { name: 'Alice', age: 20 },
  { name: 'Bob', age: 30 },
  { name: 'Charlie', age: 25 },
  { name: 'Delta', age: 23 },
  { name: 'Echo', age: 29 }
]
Enter fullscreen mode Exit fullscreen mode

It works well.

Let's say we have to place an element that has a name Charlie at the first.

When a is Charlie, we should return -1, and when b is Charlie, we should keep it as consistency.

const objArr = [
  {
    name: "Bob",
    age: 30,
  },
  {
    name: "Delta",
    age: 23,
  },
  {
    name: "Charlie",
    age: 25,
  },
  {
    name: "Echo",
    age: 29,
  },
  {
    name: "Alice",
    age: 20,
  },
];

objArr.sort((a, b) => {
  if (a.name === "Charlie") return -1;
  if (b.name === "Charlie") return 0;
  return a.name.localeCompare(b.name);
});

console.log(objArr);
Enter fullscreen mode Exit fullscreen mode
[
  { name: 'Charlie', age: 25 },
  { name: 'Alice', age: 20 },
  { name: 'Bob', age: 30 },
  { name: 'Delta', age: 23 },
  { name: 'Echo', age: 29 }
]
Enter fullscreen mode Exit fullscreen mode

That's it!
I hope you found it useful.

Happy Coding!

Top comments (0)