vendredi 27 février 2015

Can you sort an array of opaque object instances in JavaScript? NOT by a property


THIS IS NOT A QUESTION OF SORTING BY A PROPERTY!!


Assume I have an array of object instances. Many instances are in the array more than once.



var array = [
opaqueObjectA,
opaqueObjectB,
opaqueObjectA,
opaqueObjectC,
opaqueObjectB,
opaqueObjectC,
opaqueObjectA,
];


I don't care about the order, I care that the objects that are the same instance end up next to each other. In other words after sorting, one possible result would be



var array = [
opaqueObjectB,
opaqueObjectB,
opaqueObjectC,
opaqueObjectC,
opaqueObjectA,
opaqueObjectA,
opaqueObjectA,
];


I don't care if the A's or the B's or the C's come first, I only care that objects of the same instance are next to each other after sorting.


So the questions are




  1. is JavaScript sort guaranteed to handle this case?




  2. If not how can I do it? The sort function requires me to return -1 if a < b, 1 of a > b and 0 if a === b but given the objects are opaque, and since I don't have access to pointer values or something else, I have nothing to compare them with to get a less than or greater than result, only an equal result.




I can go add some sortId to each opaque object but that seems kind of bad to add properties to objects, I'd have no idea if I'm cobbering a property. I could make another set of objects, each with an id and a reference to one instance, sort those, then collect their instances into a new array. That also seems rather lame to have to go build an entire array of objects to sort.


Actually I'd also like to be able to sort by multiple instances which is a property but still not comparable. Example:



var array = [
{ thing: opaqueThingA, stuff: opaqueStuffG, },
{ thing: opaqueThingA, stuff: opaqueStuffH, },
{ thing: opaqueThingB, stuff: opaqueStuffG, },
{ thing: opaqueThingC, stuff: opaqueStuffG, },
{ thing: opaqueThingB, stuff: opaqueStuffH, },
{ thing: opaqueThingA, stuff: opaqueStuffG, },
{ thing: opaqueThingA, stuff: opaqueStuffH, },
{ thing: opaqueThingC, stuff: opaqueStuffG, },
];


I'd like to be able to sort them first by thing, then by stuff. So one possible result would be



var array = [
{ thing: opaqueThingB, stuff: opaqueStuffG, },
{ thing: opaqueThingB, stuff: opaqueStuffH, },
{ thing: opaqueThingA, stuff: opaqueStuffG, }, // Note the G' s
{ thing: opaqueThingA, stuff: opaqueStuffG, }, // Are next to
{ thing: opaqueThingA, stuff: opaqueStuffH, }, // each other
{ thing: opaqueThingA, stuff: opaqueStuffH, },
{ thing: opaqueThingC, stuff: opaqueStuffG, },
{ thing: opaqueThingC, stuff: opaqueStuffG, },
];


This would be trivial in C/C++ because I could just compare the addresses of the instances. Is there a way to do this in JavaScript without dirtying the objects with hacked on properties and without making temporary arrays just for sorting?





Aucun commentaire:

Enregistrer un commentaire