4000 Stimmen

Array von Objekten nach String-Eigenschaftswert sortieren

Ich habe ein Array von JavaScript-Objekten:

var objs = [ 
    { first_nom: 'Lazslo', last_nom: 'Jamf'     },
    { first_nom: 'Pig',    last_nom: 'Bodine'   },
    { first_nom: 'Pirate', last_nom: 'Prentice' }
];

Wie kann ich sie nach dem Wert von last_nom in JavaScript?

Ich weiß von sort(a,b) aber das scheint nur bei Strings und Zahlen zu funktionieren. Muss ich ein toString() Methode für meine Objekte?

8 Stimmen

Mit diesem Skript können Sie genau das tun, es sei denn, Sie möchten Ihre eigene Vergleichsfunktion oder Ihren eigenen Sortierer schreiben: thomasfrank.se/sortierung_der-dinge.html

0 Stimmen

Der schnellste Weg ist die Verwendung der isomorphen sort-array Modul, das nativ sowohl im Browser als auch im Node funktioniert und jede Art von Eingabe, berechnete Felder und benutzerdefinierte Sortierreihenfolgen unterstützt.

0 Stimmen

Function compare( a, b ) { if ( a.last_nom < b.last_nom ){ return -1; } if ( a.last_nom > b.last_nom ){ return 1; } return 0; } objs.sort( compare );

3voto

Jadli Punkte 820

Diese Sortierfunktion kann für alle Objektsortierungen verwendet werden,

  • Objekt

  • deepObject

  • numerische Anordnung

Sie können auch eine aufsteigende oder absteigende Sortierung durchführen, indem Sie 1,-1 als Parameter übergeben

Object.defineProperty(Object.prototype, 'deepVal', {
    enumerable: false,
    writable: true,
    value: function (propertyChain) {
        var levels = propertyChain.split('.');
        parent = this;
        for (var i = 0; i < levels.length; i++) {
            if (!parent[levels[i]])
                return undefined;
            parent = parent[levels[i]];
        }
        return parent;
    }
});

function dynamicSortAll(property,sortOrders=1) {

/**default sorting will be ascending order if you need descending order
sording you have to pass -1 as param**/

    var sortOrder = sortOrders;

    return function (a,b) {

         var result =(property? ((a.deepVal(property) > b.deepVal(property)) ? 1 : (a.deepVal(property) < b.deepVal(property)) ? -1 : 0) :((a > b) ? 1 : (a < b) ? -1 : 0))

        return result * sortOrder;

    }
}

deepObj = [
    {
        a: { a: 1, b: 2, c: 3 },
        b: { a: 4, b: 5, c: 6 }
    },
    { 
        a: { a: 3, b: 2, c: 1 },
        b: { a: 6, b: 5, c: 4 }
}];

let deepobjResult=deepObj.sort(dynamicSortAll('a.a',1))
console.log('deepobjResult :'+ JSON.stringify(deepobjResult))
var obj = [ 
    { first_nom: 'Lazslo', last_nom: 'Jamf'     },
    { first_nom: 'Pig',    last_nom: 'Bodine'   },
    { first_nom: 'Pirate', last_nom: 'Prentice' }
];
let objResult=obj.sort(dynamicSortAll('last_nom',1))
console.log('objResult :'+ JSON.stringify(objResult))

var numericObj=[1,2,3,4,5,6]

let numResult=numericObj.sort(dynamicSortAll(null,-1))
console.log('numResult :'+ JSON.stringify(numResult))

let stringSortResult='helloworld'.split('').sort(dynamicSortAll(null,1))

 console.log('stringSortResult:'+ JSON.stringify(stringSortResult))

let uniqueStringOrger=[...new Set(stringSortResult)]; 
 console.log('uniqueStringOrger:'+ JSON.stringify(uniqueStringOrger))

3voto

Morteza Tourani Punkte 3298

Ich habe gerade verbessert Ege Özcan dynamischen Art, um tief in Objekte einzutauchen. Wenn Daten wie folgt aussehen:

obj = [
    {
        a: { a: 1, b: 2, c: 3 },
        b: { a: 4, b: 5, c: 6 }
    },
    { 
        a: { a: 3, b: 2, c: 1 },
        b: { a: 6, b: 5, c: 4 }
}];

und wenn Sie sie sortieren wollen a.a Eigenschaft Ich denke, dass meine Verbesserung sehr gut hilft. Ich füge Objekten wie diesen neue Funktionen hinzu:

Object.defineProperty(Object.prototype, 'deepVal', {
    enumerable: false,
    writable: true,
    value: function (propertyChain) {
        var levels = propertyChain.split('.');
        parent = this;
        for (var i = 0; i < levels.length; i++) {
            if (!parent[levels[i]])
                return undefined;
            parent = parent[levels[i]];
        }
        return parent;
    }
});

und geändert _dynamicSort 's return Funktion:

return function (a,b) {
        var result = ((a.deepVal(property) > b.deepVal(property)) - (a.deepVal(property) < b.deepVal(property)));
        return result * sortOrder;
    }

Und jetzt können Sie sortieren nach a.a. auf diese Weise:

obj.sortBy('a.a');

Siehe Skript Commplete in JSFiddle

3voto

Kamil Kiełczewski Punkte 69048

Tief

Basierend auf este ausgezeichnetes Tutorial, das ich gerne entwickeln würde Antwort von Vlad Bezden und erklären, warum localeCompare ist besser als die Standard-Vergleichsmethode wie strA > strB . Führen wir dieses Beispiel aus

console.log( 'Österreich' > 'Zealand' );  // We expect false
console.log( 'a' > 'Z' );                 // We expect false

Der Grund dafür ist, dass in JS alle Zeichenketten mit UTF-16 und

let str = '';

// order of characters in JS
for (let i = 65; i <= 220; i++) {
  str += String.fromCodePoint(i); // code to character
}

console.log(str);

Zuerst die Großbuchstaben (mit kleinen Codes), dann die Kleinbuchstaben und dann die Zeichen Ö (nach z ). Das ist der Grund, warum wir im ersten Schnipsel true erhalten - weil der Operator > Zeichencodes vergleichen.

Wie Sie sehen können, ist der Vergleich von Zeichen in verschiedenen Sprachen keine triviale Aufgabe - aber zum Glück unterstützen moderne Browser den Internationalisierungsstandard ECMA-402 . In JS haben wir also strA.localeCompare(strB) die die Arbeit erledigen ( -1 bedeutet strA ist kleiner als strB (1 bedeutet entgegengesetzt; 0 bedeutet gleich)

console.log( 'Österreich'.localeCompare('Zealand') ); // We expect -1
console.log( 'a'.localeCompare('Z') );                // We expect -1

Ich möchte hinzufügen, dass localeCompare unterstützt zwei Parameter: Sprache und zusätzliche Regeln

var objs = [ 
    { first_nom: 'Lazslo', last_nom: 'Jamf'     },
    { first_nom: 'Pig',    last_nom: 'Bodine'   },
    { first_nom: 'Pirate', last_nom: 'Prentice' },
    { first_nom: 'Test',   last_nom: 'jamf'     } 
];

objs.sort((a,b)=> a.last_nom.localeCompare(b.last_nom,'en',{sensitivity:'case'}))

console.log(objs);

// in '>' comparison 'Jamf' will NOT be next to 'jamf'

2voto

jmwierzbicki Punkte 157

Ich kam in Problem der Sortierung Array von Objekten, mit wechselnden Priorität der Werte, im Grunde möchte ich Array von Menschen durch ihr Alter zu sortieren, und dann durch Nachname - oder nur durch Nachname, Name. Ich denke, dass dies die einfachste Lösung im Vergleich zu anderen Antworten ist.

it' wird durch den Aufruf von sortPeoples(['array', 'of', 'properties'], reverse=false) verwendet

///////////////////////example array of peoples ///////////////////////

var peoples = [
    {name: "Zach", surname: "Emergency", age: 1},
    {name: "Nancy", surname: "Nurse", age: 1},
    {name: "Ethel", surname: "Emergency", age: 1},
    {name: "Nina", surname: "Nurse", age: 42},
    {name: "Anthony", surname: "Emergency", age: 42},
    {name: "Nina", surname: "Nurse", age: 32},
    {name: "Ed", surname: "Emergency", age: 28},
    {name: "Peter", surname: "Physician", age: 58},
    {name: "Al", surname: "Emergency", age: 58},
    {name: "Ruth", surname: "Registration", age: 62},
    {name: "Ed", surname: "Emergency", age: 38},
    {name: "Tammy", surname: "Triage", age: 29},
    {name: "Alan", surname: "Emergency", age: 60},
    {name: "Nina", surname: "Nurse", age: 58}
];

//////////////////////// Sorting function /////////////////////
function sortPeoples(propertyArr, reverse) {
        function compare(a,b) {
            var i=0;
            while (propertyArr[i]) {
                if (a[propertyArr[i]] < b[propertyArr[i]])  return -1;
                if (a[propertyArr[i]] > b[propertyArr[i]])  return 1;
                i++;
            }
            return 0;
            }
        peoples.sort(compare);
        if (reverse){
            peoples.reverse();
        }
    };

////////////////end of sorting method///////////////
function printPeoples(){
  $('#output').html('');
peoples.forEach( function(person){
 $('#output').append(person.surname+" "+person.name+" "+person.age+"<br>");
} )
}

<head>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
</head>
  <html>
  <body>
<button onclick="sortPeoples(['surname']); printPeoples()">sort by ONLY by surname ASC results in mess with same name cases</button><br>
<button onclick="sortPeoples(['surname', 'name'], true); printPeoples()">sort by surname then name DESC</button><br>
<button onclick="sortPeoples(['age']); printPeoples()">sort by AGE ASC. Same issue as in first case</button><br>
<button onclick="sortPeoples(['age', 'surname']); printPeoples()">sort by AGE and Surname ASC. Adding second field fixed it.</button><br>

    <div id="output"></div>
    </body>
  </html>

3 Stimmen

Aufgebot an Menschen s :(

0 Stimmen

Der HTML-Code ist gefälscht. Die head Element liegt außerhalb der html Element. Ist der Rest der Antwort ein Schwindel?

2voto

Marinos An Punkte 7473

Für fp-holics:

const objectSorter = (p)=>(a,b)=>((a,b)=>a>b?1:a<b?-1:0)(a[p], b[p]);
objs.sort(objectSorter('first_nom'));

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X