Sortieren Sie das Array in Javascript nach Vorname (alphabetisch)

644

Ich habe ein Array (siehe unten für ein Objekt im Array), das ich mit JavaScript nach Vorname sortieren muss. Wie kann ich es tun?

var user = {
   bio: null,
   email:  "[email protected]",
   firstname: "Anna",
   id: 318,
   lastAvatar: null,
   lastMessage: null,
   lastname: "Nickson",
   nickname: "anny"
};
Jonathan Clark
quelle
Mögliches Duplikat von Sort JavaScript Array von Objekten
Felix Kling

Antworten:

1065

Angenommen, Sie haben ein Array users. Sie können users.sorteine Funktion verwenden und übergeben, die zwei Argumente verwendet und diese vergleicht (Komparator).

Es sollte zurückkehren

  • etwas Negatives, wenn das erste Argument kleiner als das zweite ist (sollte im resultierenden Array vor dem zweiten stehen)
  • etwas Positives, wenn das erste Argument größer ist (sollte nach dem zweiten stehen)
  • 0, wenn diese beiden Elemente gleich sind.

In unserem Fall, wenn zwei Elemente sind aund bwir vergleichen wollen a.firstnameundb.firstname

Beispiel:

users.sort(function(a, b){
    if(a.firstname < b.firstname) { return -1; }
    if(a.firstname > b.firstname) { return 1; }
    return 0;
})

Dieser Code funktioniert mit jedem Typ.

Beachten Sie, dass Sie in "real life" ™ beim Vergleichen von Zeichenfolgen häufig Groß- und Kleinschreibung ignorieren, diakritische Zeichen, seltsame Symbole wie ß usw. korrekt sortieren möchten localeCompare. Weitere Antworten finden Sie zur Klarheit.

RiaD
quelle
5
Friggin awesome ... Ich sortiere eine Knotenliste nach ID ... funktioniert wie ein Zauber. Thx eine Tonne!
Cody
74
Für diejenigen, die zu einem späteren Zeitpunkt eintreten, ist die Antwort von Mrchief besser, da die Groß- und Kleinschreibung nicht berücksichtigt wird.
mlienau
25
@mlienau, ich würde es nicht besser oder schlechter nennen. Es ist nur eine andere
RiaD
19
@ RiaD fair genug. Ich kann mir nur nicht vorstellen, dass viele Fälle, in denen Elemente alphabetisch sortiert werden, einschließlich des Gehäuses, in denen "Zebra" in der Liste vor "Apfel" erscheint, sehr nützlich wären.
mlienau
15
Dieser Code funktioniert nur in englischsprachigen Ländern. In anderen Ländern sollten Sie die AntwortlocaleCompare von ovunccetin mit verwenden .
Spoike
538

Kürzester Code mit ES6!

users.sort((a, b) => a.firstname.localeCompare(b.firstname))

Die grundlegende Unterstützung von String.prototype.localeCompare () ist universell!

Nachiketha
quelle
26
Mit Abstand die beste Antwort, wenn Sie im Jahr 2017 leben
Nathanbirrell
51
Beste Antwort auch, wenn Sie im Jahr 2018 leben;)
Simone
48
Wahrscheinlich auch die beste Antwort für 2019.
Ahmad Maleki
22
2020 vielleicht? oder naaa?
Kspearrin
13
ach Mann, im Jahr 2030 überschwemmt sich die Erde und das funktioniert nur in den Bergen.
Starfs
343

Etwas wie das:

array.sort(function(a, b){
 var nameA=a.name.toLowerCase(), nameB=b.name.toLowerCase();
 if (nameA < nameB) //sort string ascending
  return -1;
 if (nameA > nameB)
  return 1;
 return 0; //default return value (no sorting)
});
Mrchief
quelle
43
Beim Sortieren von Zeichenfolgen ist 'toLowerCase ()' sehr wichtig - Großbuchstaben können sich auf Ihre Sortierung auswirken.
MarzSocks
3
Falls sich jemand fragt, was die toLowerCase beeinflusst, ist es nicht viel:'a'>'A' //true 'z'>'a' //true 'A'>'z' //false
SimplGy
14
@ SimplGy Ich würde argumentieren, dass seine Wirkung ein bisschen mehr ist, als Sie ihm zuschreiben. Wie in den Kommentaren zur akzeptierten Antwort angegeben, ist es beispielsweise wichtig zu wissen, ob Ihre Sortierfunktion die Zeichenfolge 'Zebra'höher als die Zeichenfolge sortiert. Dies geschieht 'apple', wenn Sie die nicht verwenden .toLowerCase().
PrinceTyke
1
@ PrinceTyke Ja, das ist ein guter Fall Mann. 'Z' < 'a' // trueund'z' < 'a' // false
SimplGy
2
Alle gültigen Punkte und ich würde sagen, Sortieren ist immer eine "es kommt darauf an" Sache. Wenn Sie nach Namen sortieren, spielt die Groß- und Kleinschreibung möglicherweise keine Rolle. In anderen Fällen könnte es sein. Unabhängig davon denke ich, dass es nicht schwer ist, sich an die spezifische Situation anzupassen, wenn man erst einmal die Kernidee hat.
Mrchief
335

Wenn im Vergleich Strings Unicode - Zeichen enthalten können Sie mit localeCompareFunktion der StringKlasse wie folgt aus :

users.sort(function(a,b){
    return a.firstname.localeCompare(b.firstname);
})
Ovunccetin
quelle
3
String.localeCompare unterstützt Safari und IE <11 nicht :)
CORSAIR
13
@CORSAIR es wird unterstützt, es ist nur der zweite und dritte Parameter, die nicht unterstützt werden.
Codler
6
@CORSAIR Die Verwendung im Beispiel wird in allen gängigen IE-Browsern unterstützt: developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/… . LocaleCompare berücksichtigt auch die Großschreibung, daher denke ich, dass diese Implementierung als Best Practice angesehen werden sollte.
Matt Jensen
9
users.sort ((a, b) => a.firstname.localeCompare (b.firstname)) // Kurze n süße ES6-Version!
Nachiketha
4
Panzer bro. in ES6 verwendenusers.sort((a, b) => a.name.localeCompare(b.name))
Mohmmad Ebrahimi Aval
32

Netter kleiner ES6 Einzeiler:

users.sort((a, b) => a.firstname !== b.firstname ? a.firstname < b.firstname ? -1 : 1 : 0);
Sam Logan
quelle
2
Dieser ist unvollständig, da er gleiche Werte nicht richtig behandelt.
Karl-Johan Sjögren
1
Natürlich, danke, dass du das entdeckt hast, ich habe einen Check für übereinstimmende Werte hinzugefügt
Sam Logan
Nicht schlecht, ich denke, wenn Sie wirklich alles in einer Zeile haben wollen, werden verschachtelte Ternäre für die Lesbarkeit verwirrend
Russter
24

Wir können localeCompare verwenden, müssen aber auch die Schlüssel auf Falsey-Werte überprüfen

Der folgende Code funktioniert nicht, wenn in einem Eintrag lname fehlt.

obj.sort((a, b) => a.lname.localeCompare(b.lname))

Wir müssen also wie unten nach dem Falsey-Wert suchen

let obj=[
{name:'john',lname:'doe',address:'Alaska'},
{name:'tom',lname:'hopes',address:'California'},
{name:'harry',address:'Texas'}
]
let field='lname';
console.log(obj.sort((a, b) => (a[field] || "").toString().localeCompare((b[field] || "").toString())));

ODER

Wir können Lodash verwenden, es ist sehr einfach. Es erkennt die zurückgegebenen Werte, dh ob Zahl oder Zeichenfolge, und sortiert entsprechend.

import sortBy from 'lodash/sortBy';
sortBy(obj,'name')

https://lodash.com/docs/4.17.5#sortBy

sumit
quelle
2
Lodash ist ziemlich ordentlich! Hatte noch nie davon gehört. Funktioniert super!
Derk Jan Speelman
15

underscorejs bietet die sehr schöne Funktion _.sortBy:

_.sortBy([{a:1},{a:3},{a:2}], "a")

oder Sie können eine benutzerdefinierte Sortierfunktion verwenden:

_.sortBy([{a:"b"},{a:"c"},{a:"a"}], function(i) {return i.a.toLowerCase()})
Peter T.
quelle
2
Das zweite Beispiel beinhaltet die Rückgabe von Zeichenfolgen. Ist die sortByErkennung der zurückgegebenen Werte Zeichenfolgen und führt daher eine alphabetische Sortierung durch? Vielen Dank
Superjos
12

Wenn wir Namen oder etwas mit Sonderzeichen wie ñ oder áéíóú (Commons auf Spanisch) sortieren, können wir die params- Gebietsschemas ( in diesem Fall es für Spanisch) und folgende Optionen verwenden :

let user = [{'firstname': 'Az'},{'firstname': 'Áb'},{'firstname':'ay'},{'firstname': 'Ña'},{'firstname': 'Nz'},{'firstname': 'ny'}];


user.sort((a, b) => a.firstname.localeCompare(b.firstname, 'es', {sensitivity: 'base'}))


console.log(user)

Die offiziellen Gebietsschemaoptionen finden Sie hier in iana , es (Spanisch), de (Deutsch), fr (Französisch). Über Empfindlichkeit Basismittel:

Nur Zeichenfolgen, die sich in den Basisbuchstaben unterscheiden, werden als ungleich verglichen. Beispiele: a ≠ b, a = á, a = A.

Emeeus
quelle
8

Grundsätzlich können Sie Arrays mit der Methode sort sortieren. Wenn Sie jedoch Objekte sortieren möchten, müssen Sie die Funktion übergeben, um die Methode des Arrays zu sortieren. Daher werde ich Ihnen ein Beispiel für die Verwendung Ihres Arrays geben

user = [{
bio: "<null>",
email: "[email protected]",
firstname: 'Anna',
id: 318,
"last_avatar": "<null>",
"last_message": "<null>",
lastname: 'Nickson',
nickname: 'anny'
},
{
bio: "<null>",
email: "[email protected]",
firstname: 'Senad',
id: 318,
"last_avatar": "<null>",
"last_message": "<null>",
lastname: 'Nickson',
nickname: 'anny'
},
{
bio: "<null>",
email: "[email protected]",
firstname: 'Muhamed',
id: 318,
"last_avatar": "<null>",
"last_message": "<null>",
lastname: 'Nickson',
nickname: 'anny'
}];

var ar = user.sort(function(a, b)
{
  var nA = a.firstname.toLowerCase();
  var nB = b.firstname.toLowerCase();

  if(nA < nB)
    return -1;
  else if(nA > nB)
    return 1;
 return 0;
});
Senad Meškin
quelle
Warum am Ende 0 zurückgeben?
Nobita
=, wenn die Saiten gleich sind
Senad Meškin
aber in diesem Fall sollte das elsenicht entfernt werden? Sonst return 0wird das nie gelesen
Nobita
2
das ist nicht "sonst", es ist "sonst wenn"
Senad Meškin
8

Inspiriert von dieser Antwort,

users.sort((a,b) => (a.firstname  - b.firstname));
Isuru Siriwardana
quelle
8

Eine kompaktere Notation:

user.sort(function(a, b){
    return a.firstname === b.firstname ? 0 : a.firstname < b.firstname ? -1 : 1;
})
James Andrews
quelle
Es ist kompakter, verstößt aber gegen seinen Vertrag: sign(f(a, b)) =-sign(f(b, a))(für a = b)
RiaD
3
Rückkehr a.firstname == b.firstnamesollte der ===Vollständigkeit
halber
6

Auch für asec und desc sort können Sie Folgendes verwenden: Angenommen, wir haben eine Variable SortType , die die gewünschte aufsteigende oder absteigende Sortierung angibt:

 users.sort(function(a,b){
            return   sortType==="asc"? a.firstName.localeCompare( b.firstName): -( a.firstName.localeCompare(  b.firstName));
        })
ghazaleh javaheri
quelle
5

Eine verallgemeinerte Funktion kann wie folgt geschrieben werden

    function getSortedData(data, prop, isAsc) {
        return data.sort((a, b) => (a[prop] < b[prop] ? -1 : 1) * (isAsc ? 1 : -1));
   }

Sie können die folgenden Parameter übergeben

  1. Die Daten, die Sie sortieren möchten
  2. Die Eigenschaft in den Daten sollte danach sortiert werden
  3. Der letzte Parameter ist vom booleschen Typ. Es wird geprüft, ob Sie nach aufsteigend oder absteigend sortieren möchten
Santosh
quelle
4

Versuchen

users.sort((a,b)=> (a.firstname>b.firstname)*2-1)

Kamil Kiełczewski
quelle
2
Die Sortierfunktion sollte -1,0,1 zurückgeben. Dieser gibt nur -1,1 zurück.
Radu Luncasu
@RaduLuncasu - Können Sie Testdaten (Benutzerarray) bereitstellen, die zeigen, dass die obige Lösung ein falsches Ergebnis liefert? (Soweit ich weiß, ist das Fehlen von Null kein Problem)
Kamil Kiełczewski
Wenn compareFunction (a, b) 0 zurückgibt, lassen Sie a und b unverändert zueinander, aber sortiert nach allen verschiedenen Elementen.
Radu Luncasu
@RaduLuncasu ok, aber diese Informationen bedeuten nicht, dass Null obligatorisch ist. Der beste Weg, dies zu zeigen, ist die Vorbereitung von Daten, die nicht funktionieren - aber soweit ich weiß, ist dies unmöglich - zB[9,8,7,6,5,1,2,3].sort((a,b) => a<b ? -1 : 1)
Kamil Kiełczewski
3

Sie können dies für Objekte verwenden

transform(array: any[], field: string): any[] {
return array.sort((a, b) => a[field].toLowerCase() !== b[field].toLowerCase() ? a[field].toLowerCase() < b[field].toLowerCase() ? -1 : 1 : 0);}
Andre Coetzee
quelle
2

In einfachen Worten können Sie diese Methode verwenden

users.sort(function(a,b){return a.firstname < b.firstname ? -1 : 1});
FarukT
quelle
1

Sie können die eingebaute Array-Methode - verwenden sort. Diese Methode verwendet eine Rückrufmethode als Parameter



    // custom sort function to be passed as param/callback to the Array's sort method
    function myCustomSort(a, b) {
        return (a.toLowerCase() > b.toLowerCase()) ? 1 : -1;
    }

    // Actual method to be called by entity that needs sorting feature
    function sortStrings() {
        var op = Array.prototype.sort.call(arguments, myCustomSort);
    }

    // Testing the implementation
    var sortedArray = sortStrings("Burger", "Mayo1", "Pizza", "boxes", "Apples", "Mayo");
    console.log(sortedArray); //["Apples", "boxes", "Burger", "Mayo", "Mayo1", "Pizza"]


Wichtige Punkte zum Verständnis dieses Codes.

  1. In diesem Fall myCustomSortsollte die benutzerdefinierte Methode für jedes Elementpaar (aus dem Eingabearray) einen Vergleich von +1 oder -1 zurückgeben.
  2. Verwenden Sie toLowerCase()/ toUpperCase()in der benutzerdefinierten Sortierrückrufmethode, damit der Unterschied zwischen Groß- und Kleinschreibung die Richtigkeit des Sortiervorgangs nicht beeinträchtigt.

Ich hoffe, das ist klar genug. Fühlen Sie sich frei zu kommentieren, wenn Sie denken, dass weitere Informationen benötigt werden.

Prost!

shanky
quelle
Keine richtige Antwort, da nur weniger als und mehr als Prüfungen und nicht die gleiche Prüfung durchgeführt werden.
Steel Brain
Es bringt auch nichts Neues auf den Tisch, verglichen mit den Antworten, die seit ~ 2011 dort stehen.
Amenthes
1

Schob die Top-Antworten in einen Prototyp, um nach Schlüssel zu sortieren.

Array.prototype.alphaSortByKey= function (key) {
    this.sort(function (a, b) {
        if (a[key] < b[key])
            return -1;
        if (a[key] > b[key])
            return 1;
        return 0;
    });
    return this;
};
msponagle
quelle
0

Sie können etwas Ähnliches verwenden, um die Groß- und Kleinschreibung zu entfernen

users.sort(function(a, b){

  //compare two values
  if(a.firstname.toLowerCase() < b.firstname.toLowerCase()) return -1;
  if(a.firstname.toLowerCase() > b.firstname.toLowerCase()) return 1;
  return 0;

})
SAN_WEB
quelle
7
Gleiche Antwort wie die von Mrchief. Mit dem weiteren Nachteil, dass der toLowerCase viermal pro Vergleich statt zweimal durchgeführt wird.
Amenthes
0

Meine Implementierung funktioniert hervorragend in älteren ES-Versionen:

sortObject = function(data) {
    var keys = Object.keys(data);
    var result = {};

    keys.sort();

    for(var i = 0; i < keys.length; i++) {
        var key = keys[i];

        result[key] = data[key];
    }

    return result;
};
extrem
quelle
0

Nur für den Datensatz, wenn Sie eine benannte Sortierfunktion haben möchten, lautet die Syntax wie folgt:

let sortFunction = (a, b) => {
 if(a.firstname < b.firstname) { return -1; }
 if(a.firstname > b.firstname) { return 1; }
 return 0;
})
users.sort(sortFunction)

Beachten Sie, dass Folgendes NICHT funktioniert:

users.sort(sortFunction(a,b))
Katinka Hesselink
quelle