First one is to randomly sort the array (shuffle):

//———————————-

function sortRandom(a,b) {

return 0.5 – Math.random();

}

//———————————-

I needed to sort a set of letters, which might contain Turkish specific characters or a “?” (joker letter), in a Facebook application. I don’t remember if there is a simpler way to do it, but any way here is my solution with a custom sort function:

//———————————-

function sortTR(a,b){

switch (a) {

case ‘Ç': a=’CA'; break;

case ‘Ğ': a=’GA'; break;

case ‘İ': a=’IA'; break;

case ‘Ö': a=’OA'; break;

case ‘Ş': a=’SA'; break;

case ‘Ü': a=’UA'; break;

case ‘?': a=’ZA'; break;

}

switch (b) {

case ‘Ç': b=’CA'; break;

case ‘Ğ': b=’GA'; break;

case ‘İ': b=’IA'; break;

case ‘Ö': b=’OA'; break;

case ‘Ş': b=’SA'; break;

case ‘Ü': b=’UA'; break;

case ‘?': b=’ZA'; break;

}

if (a>b)

return 1;

if (a==b)

return 0;

if (a<b)

return -1;

}

//———————————-

Math.pow(p1.x-p2.x,2)+Math.pow(p1.y-p2.y,2)

is the same as:

(p1.x-p2.x)*(p1.x-p2.x)+(p1.y-p2.y)*(p1.y-p2.y)

Speaking of special cases, since we compare the distances of those points relative to one specific point which happens to lie on the origin, we can simplify the calculations even further.

locations.sort(

function(a, b) {

return (a.x+a.y)*(a.x+a.y) – (b.x+b.y)*(b.x+b.y);

}

);

That’s 8 function calls less per comparison.

Surprisingly, this still isn’t the optimal solution. The distances are calculated each time you compare two objects and sorting isn’t linear (it’s typically O(n log n) to O(n²)).

You can cheat around that by augmenting those objects with an extra property which stores that value you want to use for comparison. This way the calculations only need to be performed once.

So, if you have many items and a computationally expensive comparison function, you might want to give that approach a try.

]]>Same thing goes for circle/circle collision detection for example. You only need to know if the squared distance is smaller than the sum of the radii squared; the actual distance isn’t of any interest, which means the expensive sqrt call can be avoided.

]]>I respectfully disagree that this is the “smart” thing to do.

I think it’s better that sort has a specific well-defined behavior. I always know what calling sort on an array in JS will do.

If I need a different behavior, it’s trivial to implement and it will probably make my intentions more explicit.

As it is now, any time I see

bar.sort();

I know exactly what’s going on…for *any* value of bar[…].

If I see:

bar.sort(numeric);

I know that the standard functionality is being modified.

If we follow PHP’s lead

foo.sort();

is unclear.

Not to mention what happens if the array is comprised of mixed types. ]]>