Leaderboard
Javascript May 8, 2026
Javascript Sort Numbers Default Alphabetical Bug

JavaScript Array.sort() — Why is the Order Wrong?

This is a daily Javascript challenge from the CodeShot archive. Practice your knowledge of Sort Numbers Default Alphabetical Bug and improve your technical interview readiness.

const nums = [10, 9, 2, 21, 3]
nums.sort()
console.log(nums)
A sort() needs .reverse() after it
B sort() converts items to strings — 10 comes before 2 alphabetically
C The array needs to be copied first
D console.log should be console.dir

Detailed Explanation

Why This Question Matters

If you've been coding in JavaScript for a while, you've probably hit this wall. You have an array of numbers, you call .sort(), and suddenly 10 comes before 2. You check your logic, you restart the server, and it still happens.

The problem is that JavaScript’s sort() method doesn't actually "know" it's dealing with numbers. By default, it treats every element as a string. This is one of those "gotcha" moments in the language that trips up beginners and catches seasoned devs off guard when they're rushing through a feature. Understanding how this works is the difference between a bug that takes ten minutes to fix and a bug that haunts your production logs for a week.

Understanding the Code

Let's look at the snippet:

const nums = [10, 9, 2, 21, 3]
nums.sort()
console.log(nums)

At first glance, this looks perfect. You have an array, you call the built-in sort method, and you log the result. But if you run this, you won't get [2, 3, 9, 10, 21]. Instead, you'll get:

[10, 2, 21, 3, 9]

Wait, what? Why is 10 smaller than 2?

Here is what's happening under the hood: JavaScript converts the elements of the array into strings and then compares their sequences of UTF-16 code unit values. It’s doing a lexicographical sort (alphabetical order), not a numerical one.

In a dictionary, "Apple" comes before "Banana" because "A" comes before "B". In the same way, "10" comes before "2" because the character "1" comes before "2". The engine doesn't care that the value is ten; it only sees that the string starts with a one.

Finding the Correct Answer

To fix this, you can't just call .sort(). You need to provide a compare function.

The correct way to sort numbers in ascending order is:

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

Here is why this works. The sort() method accepts an optional function that defines the sort order. This function takes two elements (a and b) and expects a return value:

- If the result is negative, a is sorted before b.
- If the result is positive, b is sorted before a.
- If the result is zero, the order stays the same.

When you do a - b, you're creating a mathematical rule. If a is 2 and b is 10, 2 - 10 equals -8. Since that's negative, the engine knows 2 should come first. If a is 21 and b is 3, 21 - 3 is 18 (positive), so 3 gets pushed to the front.

If you wanted to sort from biggest to smallest (descending), you'd simply flip it to b - a.

Common Mistakes Developers Make

The biggest mistake is assuming sort() is "smart." Many devs assume the language will look at the data types in the array and decide the best sorting algorithm. JavaScript doesn't do that.

Another common trip-up is mutation. The .sort() method sorts the array *in place*. This means it changes the original array. If you're working in a React state or using Redux, mutating an array directly can lead to bugs where your UI doesn't re-render because the reference to the array hasn't changed.

If you need to keep the original array intact, you should copy it first:

const sorted = [...nums].sort((a, b) => a - b);

Lastly, be careful with undefined or null values in your arrays. a - b can result in NaN if one of the values isn't a number, which leads to unpredictable sorting behavior.

Real-World Usage

In a real production app, you rarely sort a simple list of five numbers. You're usually sorting an array of objects—like a list of products by price or users by join date.

The logic remains the same, but the syntax changes slightly. You have to access the property you want to compare:

const products = [
  { name: 'Keyboard', price: 120 },
  { name: 'Mouse', price: 40 },
  { name: 'Monitor', price: 300 },
];

products.sort((a, b) => a.price - b.price);

This is the foundation for almost every "Sort by Price: Low to High" dropdown you've ever used on an e-commerce site.

Key Takeaways

- Default .sort() converts everything to strings. This is why 10 comes before 2.
- Always provide a compare function (a, b) => a - b for numerical sorting.
- Remember that .sort() mutates the original array. Use the spread operator [...] if you need a fresh copy.
- For objects, access the specific property inside the compare function.

Why this matters

Understanding Sort Numbers Default Alphabetical Bug is crucial for passing technical interviews. In real-world applications, this concept often leads to subtle bugs if not handled correctly. For more details, you can always refer to the official MDN Documentation.

📝
Reviewed by CodeShot Editorial
Every challenge is code-reviewed by senior developers to ensure accuracy and real-world relevance. Learn more.

Ready for your shot?

Join thousands of developers solving one logic puzzle every morning.

Solve Today's Challenge →