5

Why does this code

["Q", "fP", "AQ", "L"].sort((a,b) => a.localeCompare(b))

give this result:

["AQ", "fP", "L", "Q"]

I thought it would give me this (and that's what I need):

["AQ", "L", "Q", "fP"]

All uppercase letters come before lower case letters chortle.ccsu.edu/java5/Notes/chap92/ch92_2.html

7
  • And why did you think so? It does not make sense. Commented Dec 8, 2018 at 23:32
  • 4
    ["Q", "fP", "AQ", "L"].sort() would give you that output Commented Dec 8, 2018 at 23:33
  • @AdamOrlov All uppercase letters come before lower case letters chortle.ccsu.edu/java5/Notes/chap92/ch92_2.html Commented Dec 8, 2018 at 23:36
  • 1
    You would think that a.localeCompare(b, "en", {sensitivity: 'case', caseFirst: "upper"}) would work ... but it does not. Commented Dec 9, 2018 at 0:00
  • 4
    @RachidOussanaa—that definition of lexicographic order is specific to Java and is not in general use. Dictionaries are not ordered with all the words starting with capital letters first, then all the lower case. They've been around for centuries. It just so happens that the ASCII code sequence for alphabetic characters lists the capitals before lower case. localeCompare tries to address that. Commented Dec 9, 2018 at 0:36

4 Answers 4

4

Don't use localeCompare(), just use sort() directly

let myArray = ["Q", "fP", "AQ", "L"];
myArray.sort();
console.log(myArray);

Interestingly enough, the following works in NodeJS, but not in Browser JavaScript. This is because the ECMAScript standard doesn't dictate which sorting algorithm to use, so it's up the each browser and/or NodeJS to dictate

let myArray = ["Q", "fP", "AQ", "L"];
myArray.sort((a, b) => a > b);
console.log(myArray);

NodeJS Demo

https://repl.it/@AnonymousSB/SO53688028

Documentation

http://www.ecma-international.org/ecma-262/5.1/#sec-15.4.4.11

Sign up to request clarification or add additional context in comments.

4 Comments

Your last comment doesn't make sense. NodeJS and JavaScript are based on ECMAScript, so there should be zero differences for built-in methods. Both your above snippets sort with "fP" after all the other strings in every browser ECMAScript implementation I tried. Also, (a, b) => a > b will not sort consistently as it will return false (0) where a == b and where a < b, rather than 0 and -1 respectively, which is what it should return.
If the compare function is undefined, the internal sortCompare function should be used, which is effectively using < and > so the abstract relational comparison algorithm is used, which falls back to code units, so not implementation dependent at all. The nodejs demo sorts exactly as browsers do.
I don't see that at all. Running the code in your demo sorts as [ 'AQ', 'L', 'Q', 'Q', 'fP' ]. The lines in the V8 code implement the sort per ECMA-262 using < and >, which sorts on code unit, not lexicographically (because ASCII code units aren't in lexicographic order). And surely `${a} < ${b}`, a > b should be `${a} < ${b}`, a < b.
Because your sort function is broken, as I said earlier. Just sort it as myArray.sort() and the result is consistent. You'll get identical results if you fix your sort function as return a < b? -1 : a > b? 1 : 0;, which is what the built–in sort function does.
2

Try this:

let myArray = ["Q", "fP", "AQ", "L"];
myArray.sort((a, b) => a > b ? 1 : -1);
console.log(myArray);

Comments

0

Don't use localeCompare(), just use sort() directly. As below:

["Q", "fP", "AQ", "L"].sort();

Comments

0

Array.prototype.sort()

sort(compareFn)

sort algorithm is implentation specific.you can supply an optional compareFn. for example

  ["Q", "fP", "AQ", "L"].sort((a,b)=>{return a - b;});

If compareFn is not supplied, all non-undefined array elements are sorted by converting them to strings and comparing strings in UTF-16 code units order

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.