So sortieren Sie ein Array von Ganzzahlen richtig

847

Der Versuch, den höchsten und niedrigsten Wert aus einem Array zu erhalten, von dem ich weiß, dass es nur Ganzzahlen enthält, scheint schwieriger zu sein, als ich dachte.

var numArray = [140000, 104, 99];
numArray = numArray.sort();
alert(numArray)

Ich würde erwarten, dass sich das zeigt 99, 104, 140000. Stattdessen zeigt es 104, 140000, 99. Es scheint also, dass die Sortierung die Werte als Zeichenfolgen behandelt.

Gibt es eine Möglichkeit, die Sortierfunktion dazu zu bringen, tatsächlich nach ganzzahligen Werten zu sortieren?

Peirix
quelle
10
Beachten Sie, dass keine der Top-Antworten alle Gleitkommawerte korrekt behandelt. insbesondere handhabt keiner von ihnen NaN. Es wäre schön, eine hochrangige Antwort zu sehen, die sich damit befasst NaN.
Quuxplusone
3
Übrigens, wenn Sie viele, viele ganze Zahlen sortieren, ist es vorteilhaft, einen ganzzahligen Sortieralgorithmus wie das Zählen der Sortierung zu verwenden . Die Sortierung der Zeitzählung dauert, bis die Skalen linear mit der Größe Ihres Arrays ausgeführt werden: O (n). Während alle Lösungen hier eine weniger effiziente Vergleichssortierung verwenden: O (n * log n).
Web_Designer
1
@Web_Designer Die Zählsortierung ist in Bezug auf den Nummernkreis linear, nicht in Bezug auf das Array. Zum Beispiel dauert das Sortieren von [1.1000000] mehr als zwei Schritte, da der Algorithmus jeden Array-Index zwischen 1 und 1000000 scannen muss, um festzustellen, welcher
Zellenwert
2
@yters Mit einer Hashmap können Sie nur auf die Ganzzahlen achten, die im zu sortierenden Array angezeigt werden. Dies macht die Sortierung linear zur Arraygröße.
Kevin
1
Am schnellsten ist es, das isomorphe Sort-Array- Modul zu verwenden, das sowohl im Browser als auch im Knoten nativ funktioniert und jede Art von Eingabe, berechneten Feldern und benutzerdefinierten Sortierreihenfolgen unterstützt.
Lloyd

Antworten:

1235

Standardmäßig sortiert die Sortiermethode Elemente alphabetisch. Um numerisch zu sortieren, fügen Sie einfach eine neue Methode hinzu, die numerische Sortierungen verarbeitet (sortNumber, siehe unten) -

var numArray = [140000, 104, 99];
numArray.sort(function(a, b) {
  return a - b;
});

console.log(numArray);

In ES6 können Sie dies mit Pfeilfunktionen vereinfachen:

numArray.sort((a, b) => a - b); // For ascending sort
numArray.sort((a, b) => b - a); // For descending sort

Dokumentation:

Mozilla Array.prototype.sort()empfiehlt diese Vergleichsfunktion für Arrays, die weder Infinity noch NaN enthalten. (WeilInf - Inf NaN ist, nicht 0).

Auch Beispiele zum Sortieren von Objekten nach Schlüsseln.

aks
quelle
148
Nett. Aber gibt es wirklich keine sofort einsatzbereite Möglichkeit, eine numerische Sortierung aus Javascript zu erhalten?
Peirix
39
ahah das ist out of the box! Wenn Sie jedoch wirklich unpraktisch sind, können Sie Funktionen ganz am Anfang Ihres Javascript an die Array-Klassenklasse binden: // Array.prototype.sortNormal = function () {return this.sort (Funktion (a, b) {return a - b})} // Wenn Sie jetzt .sortNormal () für ein beliebiges Array aufrufen, wird es numerisch sortiert
Jack Franzen
13
Warum ab und nicht a> b. Ich schlage den letzten vor, um Maschinenfehler zu vermeiden
Luca Davanzo
35
@Velthune Die Vergleichsfunktion sollte -1, 0 oder +1 zurückgeben. a> b gibt nur true oder false zurück.
Iván Pérez
48
Dieser Code kann mit einer Pfeilfunktion gekürzt werden . numberArray.sort((a, b) => (a - b));Yay! Ich denke, das ist nah an der Out-of-the-Box-Methode. Hinweis: Überprüfen Sie, ob Ihre JS-Engine Pfeilfunktionen unterstützt.
Константин Ван
173

Aufbauend auf all den oben genannten Antworten können sie auch in einer Zeile wie folgt ausgeführt werden:

var numArray = [140000, 104, 99];

// ES5
numArray = numArray.sort(function (a, b) {  return a - b;  });

// ES2015
numArray = numArray.sort((a, b) => a - b);

//outputs: 99, 104, 140000
MarzSocks
quelle
8
@bodyflex Behoben : var arr = [140000, 104, 99].sort(function(a,b) { return a-b; });. Oder kompakter, in ES6let arr = [140000, 104, 99].sort((a,b) => a-b);
00500005
1
Wie ich oben in einem Kommentar sagte, passen Pfeilfunktionen hier schlecht und ich würde jeden davon abhalten, sie auf diese Weise zu verwenden. Sie verwenden einen Nebeneffekt der Pfeils Syntax , um die Worte zu schneiden functionund ein return, sind aber nicht wirklich mit der wahren Zweck des Pfeils Funktion vorbei this. Dieser Code impliziert, dass ein gewisser thisKontext passiert, aber nicht. Verwirrend für andere Entwickler, Ihren Code zu lesen, nur um ein paar Zeichen zu sparen. Verlassen Sie sich nicht auf Nebenwirkungen - Code mit Zweck!
Bambery
12
@bambery Ich glaube nicht, dass Sie eine Pfeilfunktion ausschließlich für Kontextänderungen verwenden müssen ...
Ted Morin
7
@bambery, du verstehst tatsächlich falsch, was die Pfeilfunktion tut. Sie denken, dass es irgendwie thisin die Funktion übergeht, aber das ist nicht wahr. Es wird tatsächlich vernachlässigt, ein thisund die argumentsVariable zu erstellen , die normalerweise die übergeordneten Variablen überschreiben. Der einzige Grund, den Sie thisinnerhalb einer Pfeilfunktion verwenden können, ist das lexikalische Scoping.
Cuth
2
@bambery, der nicht gut gealtert ist ... drei Jahre später verwendet die moderne Javascript-Entwicklung fast ausschließlich Pfeilfunktionen. :)
Kip
71

array.sort führt standardmäßig eine lexikografische Sortierung durch. Für eine numerische Sortierung stellen Sie Ihre eigene Funktion bereit. Hier ist ein einfaches Beispiel:

function compareNumbers(a, b)
{
    return a - b;
}

numArray.sort(compareNumbers);

Beachten Sie auch, dass die Sortierung "an Ort und Stelle" funktioniert und die Zuweisung nicht erforderlich ist.

Paul Dixon
quelle
Ich habe den obigen Code nicht verstanden. Wie führt "return a - b" die aufsteigende Sortierung durch?
Vikramvi
Wenn a <b, gibt compareNumbers eine negative Zahl zurück. Wenn a> b, ist es positiv. Wenn gleich, gibt es 0 zurück.
Paul Dixon
38

Diese Antwort ist auf einige der vorhandenen Antworten gleichwertig, aber ECMAScript 6 Pfeil Funktionen bieten eine wesentlich kompaktere Syntax , die uns eine Inline - Sortierfunktion , ohne dabei die Lesbarkeit definieren können:

numArray = numArray.sort((a, b) => a - b);

Es wird heute in den meisten Browsern unterstützt .

jjjjs
quelle
1
"ohne die Lesbarkeit zu beeinträchtigen". Das ist subjektiv. Mit einigen einfachen ganzen Zahlen ist es lesbar. Wenn Sie mit komplexeren Objekten arbeiten und nach einer Eigenschaft sortieren möchten, nicht so sehr.
Tristan
3
@Tristan, das Sortieren nach einer Eigenschaft eines Objekts kann mit dieser Syntax immer noch ziemlich sauber durchgeführt werden. Wenn die Eigenschaft des Objekts, nach dem Sie sortieren möchten, eine Zahl ist, die Sie objArray=objArray.sort((a,b)=>a.numProperty - b.numProperty);objArray=objArray.sort((a,b)=>a.strProperty.localeCompare(b.strProperty))‌​;
ausführen
34

Ich bin überrascht, warum jeder empfiehlt, eine Komparatorfunktion zu übergeben sort(), was das Sortieren sehr langsam macht!

Um Zahlen zu sortieren, erstellen Sie einfach ein TypedArray :

var numArray = new Uint32Array([140000, 104, 99]);
numArray = numArray.sort();
alert(numArray)

dy_
quelle
4
Die Verwendung eines TypedArray beschleunigt die Sortierung um das Fünffache. Wenn Sie noch schneller gehen möchten, implementiert das npm-Paket Radix Sort und Counting Sort, die in mehreren Antworten hier vorgeschlagen werden.
DragonSpit
wow, wusste nicht, dass es das gibt!
Pixelearth
21

Der Grund, warum sich die Sortierfunktion so seltsam verhält

Aus der Dokumentation :

[...] Das Array wird nach dem Unicode-Codepunktwert jedes Zeichens und nach der Zeichenfolgenkonvertierung jedes Elements sortiert.

Wenn Sie die Unicode-Punktwerte des Arrays drucken , wird dies deutlich.

console.log("140000".charCodeAt(0));
console.log("104".charCodeAt(0));
console.log("99".charCodeAt(0));

//Note that we only look at the first index of the number "charCodeAt(  0  )"

Dies gibt zurück: "49, 49, 57".

49 (unicode value of first number at 140000)
49 (unicode value of first number at 104)
57 (unicode value of first number at 99)

Da 140000 und 104 dieselben Werte (49) zurückgegeben haben, wird der erste Index abgeschnitten und erneut überprüft:

console.log("40000".charCodeAt(0));
console.log("04".charCodeAt(0));

//Note that we only look at the first index of the number "charCodeAt(  0  )"

52 (unicode value of first number at 40000)
40 (unicode value of first number at 04)

Wenn wir das sortieren, erhalten wir:

40 (unicode value of first number at 04)
52 (unicode value of first number at 40000)

also kommt 104 vor 140000.

Das Endergebnis wird also sein:

var numArray = [140000, 104, 99];
numArray = numArray.sort();
console.log(numArray)

104, 140000, 99

Fazit:

sort()sortiert, indem nur der erste Index der Zahlen betrachtet wird. sort()Es ist egal, ob eine ganze Zahl größer als eine andere ist, sie vergleicht den Wert des Unicodes der Ziffern, und wenn zwei gleiche Unicode-Werte vorhanden sind, prüft sie, ob es eine nächste Ziffer gibt, und vergleicht sie ebenfalls.

Um richtig zu sortieren, müssen Sie eine Vergleichsfunktion übergeben, sort()wie hier erläutert .

Schwarz
quelle
Hinweis: Dies ist nur meine Erklärung, ich habe den Code nicht wirklich nachgeschlagen. Vertraue dieser Antwort also nicht ganz.
Schwarz
17

Ich bin mit aks einverstanden, aber anstatt zu verwenden

return a - b;

Du solltest benutzen

return a > b ? 1 : a < b ? -1 : 0;
user3587638
quelle
18
Können Sie erklären , warum jemand sollte Ihr mehr unleserlich ternären Betrieb verwenden? Soweit ich das beurteilen kann, hätte es das gleiche Ergebnis.
stefannew
6
Diese Antwort berücksichtigt auch gleiche Werte und lässt sie an derselben Stelle.
Maarten00
23
Und a - b nicht?
Bryan Rayner
12
"return ab" mag für den speziellen Fall dieser Frage (Javascript und alle als Ints bekannten Eingabeelemente) angemessen sein, aber ich persönlich bevorzuge die ternäre Form, weil sie kanonischer ist - sie funktioniert in mehr Fällen in mehr Programmiersprachen mit mehr Datentypen. ZB in C kann ab überlaufen, was zu Endlosschleifen, Speicherbeschädigungen, Abstürzen usw. führt. Allerdings funktioniert selbst die ternäre Form nicht ordnungsgemäß, wenn NaNs oder gemischte Typen beteiligt sind.
Don Hatch
8
Die >und <vergleichen immer noch a und b als Strings.
Vriesdemichael
11

In der neuen ES6-Welt ist es viel einfacher, eine Sortierung durchzuführen

numArray.sort((a,b) => a-b);

Das ist alles was du brauchst :)

Chait
quelle
10

In JavaScript besteht das Standardverhalten der sort () -Methode darin, Werte in einem Array alphabetisch zu sortieren.

Um nach Zahlen zu sortieren, müssen Sie eine numerische Sortierfunktion definieren (was sehr einfach ist):

...
function sortNumber(a, b)
{
  return a - b;
}

numArray = numArray.sort(sortNumber);
Peter Mortensen
quelle
8

Array.prototype.sort () ist die Methode zum Sortieren von Arrays, aber es gibt einige Probleme, die wir beachten müssen.

Die Sortierreihenfolge ist standardmäßig lexikografisch und nicht numerisch, unabhängig von den Wertetypen im Array. Selbst wenn das Array nur aus Zahlen besteht, werden alle Werte in Zeichenfolgen konvertiert und lexikografisch sortiert.

Müssen wir also die Methode sort () und reverse () wie unten anpassen?

Weitergeleitete URL

Zum Sortieren von Zahlen innerhalb des Arrays

numArray.sort(function(a, b)
{
    return a - b;
});

Zum Umkehren von Zahlen innerhalb des Arrays

numArray.sort(function(a, b)
{
    return b - a;
});

Weitergeleitete URL

Merbin Joe
quelle
6

Die Frage wurde bereits beantwortet, der kürzeste Weg ist die Verwendung der sort()Methode. Wenn Sie jedoch nach mehr Möglichkeiten suchen, um Ihre Zahlenreihen zu sortieren, und Sie auch Zyklen lieben, überprüfen Sie Folgendes

Sortieren durch Einfügen

Aufsteigend:

var numArray = [140000, 104, 99];
for (var i = 0; i < numArray.length; i++) {
    var target = numArray[i];
    for (var j = i - 1; j >= 0 && (numArray[j] > target); j--) {
        numArray[j+1] = numArray[j];
    }
    numArray[j+1] = target
}
console.log(numArray);

Absteigend:

var numArray = [140000, 104, 99];
for (var i = 0; i < numArray.length; i++) {
    var target = numArray[i];
    for (var j = i - 1; j >= 0 && (numArray[j] < target); j--) {
        numArray[j+1] = numArray[j];
    }
    numArray[j+1] = target
}
console.log(numArray);

Auswahlsortierung:

Aufsteigend:

var numArray = [140000, 104, 99];
for (var i = 0; i < numArray.length - 1; i++) {
    var min = i;
    for (var j = i + 1; j < numArray.length; j++) {
        if (numArray[j] < numArray[min]) {
            min = j;
        }
    }
    if (min != i) {
        var target = numArray[i];
        numArray[i] = numArray[min];
        numArray[min] = target;
    }
}
console.log(numArray);

Absteigend:

var numArray = [140000, 104, 99];
for (var i = 0; i < numArray.length - 1; i++) {
    var min = i;
    for (var j = i + 1; j < numArray.length; j++) {
        if (numArray[j] > numArray[min]) {
            min = j;
        }
    }
    if (min != i) {
        var target = numArray[i];
        numArray[i] = numArray[min];
        numArray[min] = target;
    }
}
console.log(numArray);

Habe Spaß

Kommerzieller Selbstmord
quelle
Ist diese tatsächlich schneller für kleinen Arrays als die Verwendung sort()auf einem TypedArray wie diese Antwort suggeriert . Sicherlich sind sie für mittlere bis große Arrays nicht schneller, da es sich um O (n ^ 2) -Algorithmen handelt.
Peter Cordes
5

Die folgende Funktion 'numerisch' dient in vielen Fällen dazu, ein Array von Zahlen numerisch zu sortieren, wenn sie als Rückruffunktion bereitgestellt wird:

function numerically(a, b){
    return a-b;
}

array.sort(numerically); 

In einigen seltenen Fällen, in denen das Array sehr große und negative Zahlen enthält, kann ein Überlauffehler auftreten, da das Ergebnis von ab kleiner wird als die kleinste Zahl, mit der JavaScript umgehen kann.

Eine bessere Art, numerische Funktionen zu schreiben, ist also wie folgt:

function numerically(a, b){
   if(a < b){
      return -1;
   } else if(a > b){
      return 1;
   } else {
      return 0;
   }
}
leet101
quelle
1
JavaScript-Zahlen sind Gleitkommazahlen. IEEE754 definiert Überlauf- und Unterlaufregeln, einschließlich Überlauf auf + -Infinity und Unterlauf auf subnormal oder + -0,0. Ich denke nicht, dass die Subtraktion von zwei Zahlen auf + -0,0 unterlaufen kann, selbst wenn beide groß und in der Nähe gleich sind. Der Unterschied zwischen zwei Doppelwerten kann immer als ein weiteres Doppel ungleich Null dargestellt werden (es sei denn, es DBL_MIN - DBL_MAXläuft über), aber ein Unterlauf ist nicht möglich. Durch eine katastrophale Stornierung wird das Ergebnis ungenau und verliert die meisten seiner "signifikanten Ziffern", ist jedoch a-bimmer ungleich Null und hat das richtige Vorzeichen für a! = B.
Peter Cordes
4

Undefiniert, Null und NaN behandeln: Null verhält sich wie 0, NaN und Undefiniert gehen zu Ende.

array = [3, 5, -1, 1, NaN, 6, undefined, 2, null]
array.sort((a,b) => isNaN(a) || a-b)
// [-1, null, 1, 2, 3, 5, 6, NaN, undefined]
Ali Khosro
quelle
3

Nur für ein normales Array von Elementwerten:

function sortArrayOfElements(arrayToSort) {
    function compareElements(a, b) {
        if (a < b)
            return -1;
        if (a > b)
            return 1;
        return 0;
    }

    return arrayToSort.sort(compareElements);
}

e.g. 1:
var array1 = [1,2,545,676,64,2,24]
**output : [1, 2, 2, 24, 64, 545, 676]**

var array2 = ["v","a",545,676,64,2,"24"]
**output: ["a", "v", 2, "24", 64, 545, 676]**

Für eine Reihe von Objekten:

function sortArrayOfObjects(arrayToSort, key) {
    function compareObjects(a, b) {
        if (a[key] < b[key])
            return -1;
        if (a[key] > b[key])
            return 1;
        return 0;
    }

    return arrayToSort.sort(compareObjects);
}

e.g. 1: var array1= [{"name": "User4", "value": 4},{"name": "User3", "value": 3},{"name": "User2", "value": 2}]

**output : [{"name": "User2", "value": 2},{"name": "User3", "value": 3},{"name": "User4", "value": 4}]**
Umesh
quelle
2

Aktualisieren! Scrollen Sie zum Ende der Antwort, um ein smartSortProp-Additiv zu erhalten, das noch mehr Spaß macht!
Sortiert Arrays von allem !

Meine persönliche Lieblingsform dieser Funktion ermöglicht einen Parameter für Aufsteigend oder Absteigend:

function intArraySort(c, a) {
    function d(a, b) { return b - a; }
    "string" == typeof a && a.toLowerCase();
    switch (a) {
        default: return c.sort(function(a, b) { return a - b; });
        case 1:
                case "d":
                case "dc":
                case "desc":
                return c.sort(d)
    }
};

Verwendung so einfach wie:

var ara = function getArray() {
        var a = Math.floor(Math.random()*50)+1, b = [];
        for (i=0;i<=a;i++) b.push(Math.floor(Math.random()*50)+1);
        return b;
    }();

//    Ascending
intArraySort(ara);
console.log(ara);

//    Descending
intArraySort(ara, 1);
console.log(ara);

//    Ascending
intArraySort(ara, 'a');
console.log(ara);

//    Descending
intArraySort(ara, 'dc');
console.log(ara);

//    Ascending
intArraySort(ara, 'asc');
console.log(ara);

jsFiddle


Oder Code Snippet Beispiel hier!

function intArraySort(c, a) {
	function d(a, b) { return b - a }
	"string" == typeof a && a.toLowerCase();
	switch (a) {
		default: return c.sort(function(a, b) { return a - b });
		case 1:
		case "d":
		case "dc":
		case "desc":
		return c.sort(d)
	}
};

function tableExample() {
	var d = function() {
			var a = Math.floor(50 * Math.random()) + 1,
				b = [];
			for (i = 0; i <= a; i++) b.push(Math.floor(50 * Math.random()) + 1);
			return b
		},
		a = function(a) {
			var b = $("<tr/>"),
				c = $("<th/>").prependTo(b);
			$("<td/>", {
				text: intArraySort(d(), a).join(", ")
			}).appendTo(b);
			switch (a) {
				case 1:
				case "d":
				case "dc":
				case "desc":
					c.addClass("desc").text("Descending");
					break;
				default:
					c.addClass("asc").text("Ascending")
			}
			return b
		};
	return $("tbody").empty().append(a(), a(1), a(), a(1), a(), a(1), a(), a(1), a(), a(1), a(), a(1))
};

tableExample();
table { border-collapse: collapse; }
th, td { border: 1px solid; padding: .25em .5em; vertical-align: top; }
.asc { color: red; }
.desc { color: blue }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<table><tbody></tbody></table>


.smartSort ('asc' | 'desc')

Viel Spaß mit einer Sortiermethode, die ein Array mit mehreren Elementen sortiert! Behandelt derzeit nicht "assoziativ" (auch bekannt als String-Schlüssel), aber alle Arten von Werten! Es werden nicht nur die mehreren Werte ascoder sortiertdesc entsprechend, sondern behält auch die konstante "Position" der "Wertegruppen" bei. Mit anderen Worten; Ints sind immer zuerst, dann kommen Strings, dann Arrays (ja, ich mache das mehrdimensional!), dann Objekte (ungefiltert, Element, Datum) und schließlich undefinierte und Nullen!

"Warum?" du fragst. Warum nicht!

Jetzt kommt in 2 Geschmacksrichtungen! Der erste erfordert neuere Browser Object.defineProperty, um die Methode zum Array.protoypeObjekt hinzuzufügen . Dies ermöglicht eine einfache natürliche Verwendung, wie z myArray.smartSort('a'). Wenn Sie für ältere Browser implementieren müssen oder native Objekte einfach nicht ändern möchten, scrollen Sie nach unten zur Version " Nur Methode" .

/* begin */
/* KEY NOTE! Requires EcmaScript 5.1 (not compatible with older browsers) */
;;(function(){if(Object.defineProperty&&!Array.prototype.smartSort){var h=function(a,b){if(null==a||void 0==a)return 1;if(null==b||void 0==b)return-1;var c=typeof a,e=c+typeof b;if(/^numbernumber$/ig.test(e))return a-b;if(/^stringstring$/ig.test(e))return a>b;if(/(string|number){2}/ig.test(e))return/string/i.test(c)?1:-1;if(/number/ig.test(e)&&/object/ig.test(e)||/string/ig.test(e)&&/object/ig.test(e))return/object/i.test(c)?1:-1;if(/^objectobject$/ig.test(e)){a instanceof Array&&a.smartSort("a");b instanceof Array&&b.smartSort("a");if(a instanceof Date&&b instanceof Date)return a-b;if(a instanceof Array&&b instanceof Array){var e=Object.keys(a),g=Object.keys(b),e=e.concat(g).smartSort("a"),d;for(d in e)if(c=e[d],a[c]!=b[c])return d=[a[c],b[c]].smartSort("a"),a[c]==d[0]?-1:1;var f=[a[Object.keys(a)[0]],b[Object.keys(b)[0]]].smartSort("a");return a[Object.keys(a)[0]]==f[0]?-1:1}if(a instanceof Element&&b instanceof Element){if(a.tagName==b.tagName)return e=[a.id,b.id].smartSort("a"),a.id==e[0]?1:-1;e=[a.tagName, b.tagName].smartSort("a");return a.tagName==e[0]?1:-1}if(a instanceof Date||b instanceof Date)return a instanceof Date?1:-1;if(a instanceof Array||b instanceof Array)return a instanceof Array?-1:1;e=Object.keys(a);g=Object.keys(b);e.concat(g).smartSort("a");for(c=0;20>c;c++){d=e[c];f=g[c];if(a.hasOwnProperty(d)&&b.hasOwnProperty(f)){if(a[d]instanceof Element&&b[f]instanceof Element){if(a[d].tagName==b[f].tagName)return c=[a[d].id,b[f].id].smartSort("a"),a[d].id==c[0]?-1:1;c=[a[d].tagName,b[f].tagName].smartSort("d"); return a[d].tagName==c[0]?1:-1}if(a[d]instanceof Element||b[f]instanceof Element)return a[d]instanceof Element?1:-1;if(a[d]!=b[f])return c=[a[d],b[f]].smartSort("a"),a[d]==c[0]?-1:1}if(a.hasOwnProperty(d)&&a[d]instanceof Element)return 1;if(b.hasOwnProperty(f)&&b[f]instanceof Element||!a.hasOwnProperty(d))return-1;if(!b.hasOwnProperty(d))return 1}c=[a[Object.keys(a)[0]],b[Object.keys(b)[0]]].smartSort("d");return a[Object.keys(a)[0]]==c[0]?-1:1}g=[a,b].sort();return g[0]>g[1]},k=function(a,b){if(null== a||void 0==a)return 1;if(null==b||void 0==b)return-1;var c=typeof a,e=c+typeof b;if(/^numbernumber$/ig.test(e))return b-a;if(/^stringstring$/ig.test(e))return b>a;if(/(string|number){2}/ig.test(e))return/string/i.test(c)?1:-1;if(/number/ig.test(e)&&/object/ig.test(e)||/string/ig.test(e)&&/object/ig.test(e))return/object/i.test(c)?1:-1;if(/^objectobject$/ig.test(e)){a instanceof Array&&a.smartSort("d");b instanceof Array&&b.smartSort("d");if(a instanceof Date&&b instanceof Date)return b-a;if(a instanceof Array&&b instanceof Array){var e=Object.keys(a),g=Object.keys(b),e=e.concat(g).smartSort("a"),d;for(d in e)if(c=e[d],a[c]!=b[c])return d=[a[c],b[c]].smartSort("d"),a[c]==d[0]?-1:1;var f=[a[Object.keys(a)[0]],b[Object.keys(b)[0]]].smartSort("d");return a[Object.keys(a)[0]]==f[0]?-1:1}if(a instanceof Element&&b instanceof Element){if(a.tagName==b.tagName)return e=[a.id,b.id].smartSort("d"),a.id==e[0]?-1:1;e=[a.tagName,b.tagName].smartSort("d");return a.tagName==e[0]?-1:1}if(a instanceof Date||b instanceof Date)return a instanceof Date?1:-1;if(a instanceof Array||b instanceof Array)return a instanceof Array?-1:1;e=Object.keys(a);g=Object.keys(b);e.concat(g).smartSort("a");for(c=0;20>c;c++){d=e[c];f=g[c];if(a.hasOwnProperty(d)&&b.hasOwnProperty(f)){if(a[d]instanceof Element&&b[f]instanceof Element){if(a[d].tagName==b[f].tagName)return c=[a[d].id,b[f].id].smartSort("d"),a[d].id==c[0]?-1:1;c=[a[d].tagName,b[f].tagName].smartSort("d");return a[d].tagName==c[0]?-1:1}if(a[d]instanceof Element||b[f]instanceof Element)return a[d]instanceof Element?1:-1;if(a[d]!=b[f])return c=[a[d],b[f]].smartSort("d"),a[d]==c[0]?-1:1}if(a.hasOwnProperty(d)&&a[d]instanceof Element)return 1;if(b.hasOwnProperty(f)&&b[f]instanceof Element)return-1;if(!a.hasOwnProperty(d))return 1;if(!b.hasOwnProperty(d))return-1}c=[a[Object.keys(a)[0]],b[Object.keys(b)[0]]].smartSort("d");return a[Object.keys(a)[0]]==c[0]?-1:1}g=[a,b].sort();return g[0]<g[1]};Object.defineProperty(Array.prototype,"smartSort",{value:function(){return arguments&& (!arguments.length||1==arguments.length&&/^a([sc]{2})?$|^d([esc]{3})?$/i.test(arguments[0]))?this.sort(!arguments.length||/^a([sc]{2})?$/i.test(arguments[0])?h:k):this.sort()}})}})();
/* end */

jsFiddle Array.prototype.smartSort ('asc | desc')


Die Bedienung ist einfach! Machen Sie zuerst ein verrücktes Array wie:

window.z = [ 'one', undefined, $('<span />'), 'two', null, 2, $('<div />', { id: 'Thing' }), $('<div />'), 4, $('<header />') ];
z.push(new Date('1/01/2011'));
z.push('three');
z.push(undefined);
z.push([ 'one', 'three', 'four' ]);
z.push([ 'one', 'three', 'five' ]);
z.push({ a: 'a', b: 'b' });
z.push({ name: 'bob', value: 'bill' });
z.push(new Date());
z.push({ john: 'jill', jack: 'june' });
z.push([ 'abc', 'def', [ 'abc', 'def', 'cba' ], [ 'cba', 'def', 'bca' ], 'cba' ]);
z.push([ 'cba', 'def', 'bca' ]);
z.push({ a: 'a', b: 'b', c: 'c' });
z.push({ a: 'a', b: 'b', c: 'd' });

Dann sortiere es einfach!

z.smartSort('asc'); // Ascending
z.smartSort('desc'); // Descending

Nur Methode

Wie oben, nur als einfache Methode!

/* begin */
/* KEY NOTE! Method `smartSort` is appended to native `window` for global use. If you'd prefer a more local scope, simple change `window.smartSort` to `var smartSort` and place inside your class/method */
window.smartSort=function(){if(arguments){var a,b,c;for(c in arguments)arguments[c]instanceof Array&&(a=arguments[c],void 0==b&&(b="a")),"string"==typeof arguments[c]&&(b=/^a([sc]{2})?$/i.test(arguments[c])?"a":"d");if(a instanceof Array)return a.sort("a"==b?smartSort.asc:smartSort.desc)}return this.sort()};smartSort.asc=function(a,b){if(null==a||void 0==a)return 1;if(null==b||void 0==b)return-1;var c=typeof a,e=c+typeof b;if(/^numbernumber$/ig.test(e))return a-b;if(/^stringstring$/ig.test(e))return a> b;if(/(string|number){2}/ig.test(e))return/string/i.test(c)?1:-1;if(/number/ig.test(e)&&/object/ig.test(e)||/string/ig.test(e)&&/object/ig.test(e))return/object/i.test(c)?1:-1;if(/^objectobject$/ig.test(e)){a instanceof Array&&a.sort(smartSort.asc);b instanceof Array&&b.sort(smartSort.asc);if(a instanceof Date&&b instanceof Date)return a-b;if(a instanceof Array&&b instanceof Array){var e=Object.keys(a),g=Object.keys(b),e=smartSort(e.concat(g),"a"),d;for(d in e)if(c=e[d],a[c]!=b[c])return d=smartSort([a[c], b[c]],"a"),a[c]==d[0]?-1:1;var f=smartSort([a[Object.keys(a)[0]],b[Object.keys(b)[0]]],"a");return a[Object.keys(a)[0]]==f[0]?-1:1}if(a instanceof Element&&b instanceof Element){if(a.tagName==b.tagName)return e=smartSort([a.id,b.id],"a"),a.id==e[0]?1:-1;e=smartSort([a.tagName,b.tagName],"a");return a.tagName==e[0]?1:-1}if(a instanceof Date||b instanceof Date)return a instanceof Date?1:-1;if(a instanceof Array||b instanceof Array)return a instanceof Array?-1:1;e=Object.keys(a);g=Object.keys(b);smartSort(e.concat(g), "a");for(c=0;20>c;c++){d=e[c];f=g[c];if(a.hasOwnProperty(d)&&b.hasOwnProperty(f)){if(a[d]instanceof Element&&b[f]instanceof Element){if(a[d].tagName==b[f].tagName)return c=smartSort([a[d].id,b[f].id],"a"),a[d].id==c[0]?-1:1;c=smartSort([a[d].tagName,b[f].tagName],"a");return a[d].tagName==c[0]?-1:1}if(a[d]instanceof Element||b[f]instanceof Element)return a[d]instanceof Element?1:-1;if(a[d]!=b[f])return c=smartSort([a[d],b[f]],"a"),a[d]==c[0]?-1:1}if(a.hasOwnProperty(d)&&a[d]instanceof Element)return 1; if(b.hasOwnProperty(f)&&b[f]instanceof Element||!a.hasOwnProperty(d))return-1;if(!b.hasOwnProperty(d))return 1}c=smartSort([a[Object.keys(a)[0]],b[Object.keys(b)[0]]],"a");return a[Object.keys(a)[0]]==c[0]?1:-1}g=[a,b].sort();return g[0]>g[1]};smartSort.desc=function(a,b){if(null==a||void 0==a)return 1;if(null==b||void 0==b)return-1;var c=typeof a,e=c+typeof b;if(/^numbernumber$/ig.test(e))return b-a;if(/^stringstring$/ig.test(e))return b>a;if(/(string|number){2}/ig.test(e))return/string/i.test(c)? 1:-1;if(/number/ig.test(e)&&/object/ig.test(e)||/string/ig.test(e)&&/object/ig.test(e))return/object/i.test(c)?1:-1;if(/^objectobject$/ig.test(e)){a instanceof Array&&a.sort(smartSort.desc);b instanceof Array&&b.sort(smartSort.desc);if(a instanceof Date&&b instanceof Date)return b-a;if(a instanceof Array&&b instanceof Array){var e=Object.keys(a),g=Object.keys(b),e=smartSort(e.concat(g),"a"),d;for(d in e)if(c=e[d],a[c]!=b[c])return d=smartSort([a[c],b[c]],"d"),a[c]==d[0]?-1:1;var f=smartSort([a[Object.keys(a)[0]], b[Object.keys(b)[0]]],"d");return a[Object.keys(a)[0]]==f[0]?-1:1}if(a instanceof Element&&b instanceof Element){if(a.tagName==b.tagName)return e=smartSort([a.id,b.id],"d"),a.id==e[0]?-1:1;e=smartSort([a.tagName,b.tagName],"d");return a.tagName==e[0]?-1:1}if(a instanceof Date||b instanceof Date)return a instanceof Date?1:-1;if(a instanceof Array||b instanceof Array)return a instanceof Array?-1:1;e=Object.keys(a);g=Object.keys(b);smartSort(e.concat(g),"a");for(c=0;20>c;c++){d=e[c];f=g[c];if(a.hasOwnProperty(d)&& b.hasOwnProperty(f)){if(a[d]instanceof Element&&b[f]instanceof Element){if(a[d].tagName==b[f].tagName)return c=smartSort([a[d].id,b[f].id],"d"),a[d].id==c[0]?-1:1;c=smartSort([a[d].tagName,b[f].tagName],"d");return a[d].tagName==c[0]?-1:1}if(a[d]instanceof Element||b[f]instanceof Element)return a[d]instanceof Element?1:-1;if(a[d]!=b[f])return c=smartSort([a[d],b[f]],"d"),a[d]==c[0]?-1:1}if(a.hasOwnProperty(d)&&a[d]instanceof Element)return 1;if(b.hasOwnProperty(f)&&b[f]instanceof Element)return-1; if(!a.hasOwnProperty(d))return 1;if(!b.hasOwnProperty(d))return-1}c=smartSort([a[Object.keys(a)[0]],b[Object.keys(b)[0]]],"d");return a[Object.keys(a)[0]]==c[0]?-1:1}g=[a,b].sort();return g[0]<g[1]}
/* end */

Verwenden:

z = smartSort(z, 'asc'); // Ascending
z = smartSort(z, 'desc'); // Descending

jsFiddle-Methode smartSort (Array, "asc | desc")

SpYk3HH
quelle
2

Versuchen Sie diesen Code:

HTML:

<div id="demo"></div>

JavaScript-Code:

<script>
    (function(){
        var points = [40, 100, 1, 5, 25, 10];
        document.getElementById("demo").innerHTML = points;
        points.sort(function(a, b){return a-b});
        document.getElementById("demo").innerHTML = points;
    })();
</script>
Sunny SM
quelle
2

Versuchen Sie diesen Code wie folgt

var a = [5, 17, 29, 48, 64, 21];
function sortA(arr) {
return arr.sort(function(a, b) {
return a - b;
})
;} 
alert(sortA(a));
user7125929
quelle
ist es nicht wahr
user7125929
1
var numArray = [140000, 104, 99];
numArray = numArray.sort((a,b) => a-b);
alert(numArray)
Vardaman PK
quelle
4
Willkommen bei StackOverflow. Ihre Antwort ist identisch mit der akzeptierten Antwort. Können Sie Ihrer Antwort eine Erklärung hinzufügen, um zu erklären, warum dies der akzeptierten Antwort vorgezogen werden sollte?
Einfach Ged
1

Obwohl dies in JavaScript nicht erforderlich ist, können Sie es verwenden, wenn Sie möchten , dass -1, 0 oder 1 strikt zurückgegeben wird (ähnlich wie der Raumschiffoperator in PHP funktioniert) .sort() compareFunctionMath.sign()

Das compareFunctionFolgende gibt streng -1, 0 oder 1 zurück:

numArray.sort((a, b) => Math.sign(a - b));

Hinweis: Math.sign() wird in Internet Explorer nicht unterstützt.

Grant Miller
quelle
0

Dies ist die bereits vorgeschlagene und akzeptierte Lösung als Methode für den Array-Prototyp:

Array.prototype.sortNumeric = function () {
    return this.sort((a, b) => a - b);
};
Array.prototype.sortNumericDesc = function () {
    return this.sort((a, b) => b - a);
};
Fehler 404
quelle
0

Als Sortiermethode werden Array-Elemente in Zeichenfolgen konvertiert. Im Folgenden funktioniert es also auch gut mit Dezimalzahlen mit Array-Elementen.

let productPrices = [10.33, 2.55, 1.06, 5.77];
console.log(productPrices.sort((a,b)=>a-b));

Und gibt Ihnen das erwartete Ergebnis.

Anshul Chaurasia
quelle
0

Überschreiben der Sortiermethode.

Array.prototype.sortInt = function(){
    this.sort(function(a,b){return a-b});
}


numbers = [12,8,21,5,1,34];
numbers.sortInt()
//output -> [1,5,8,12,21,34]
Sand
quelle
0

Die Standardsortierfunktion ist Sortieren in Wörterbuchreihenfolge:

var ar = [10000,3,200];
console.log(ar.sort());
//it will sort like :=> [10000, 200, 3]

Das obige ist nicht der Fall, den wir für Zahlen wollen. Wenn Sie also Ganzzahlen haben und die Standardsortierfunktion nicht funktioniert (weil sie in Wörterbuchreihenfolge sortiert), müssen Sie Ihre eigene Funktion implementieren:

var ar = [10000,3,-09,200];
function customSortHelpForNumber(number1, number2){
     return number1-number2;
}
console.log(ar.sort(customSortHelpForNumber));
//it will sort like :=> [3, 200, 10000]

Ich hoffe, Sie haben eine Frage, wie es funktioniert? Wenn wir hier eine Methode in Sortierfunktion bereitstellen, werden jedes Mal zwei Zahlen übergeben, und wenn die Zahl zurückgegeben wird

  • -ve Wert oder 0, behält die erste Zahl an ihrer Stelle
  • + ve Wert es tauschen den Ort.

Indem Sie dies für alle Zahlen befolgen, sortieren Sie das Array der Ganzzahl.

Wenn Sie ES6 verwenden, schreiben Sie eine Pfeilfunktion:

console.log(ar.sort((num1,num2)=> num1-num2));
    //it will sort like :=> [3, 200, 10000]
JustIn
quelle
-1

Hier ist meine Sortier-Array-Funktion in der Utils-Bibliothek:

sortArray: function(array) {
    array.sort(function(a, b) {
        return a > b;
    });
},

# Let's test a string array
var arr = ['bbc', 'chrome', 'aux', 'ext', 'dog'];
utils.sortArray(arr);
console.log(arr);
>>> ["aux", "bbc", "chrome", "dog", "ext", remove: function]

# Let's test a number array
var arr = [55, 22, 1425, 12, 78];
utils.sortArray(arr);
console.log(arr);
>>> [12, 22, 55, 78, 1425, remove: function]
Feuerschlag
quelle
3
Das ist einfach falsch! Die Sortierfunktion muss negative, 0 oder positive Zahlen zurückgeben, nicht wahr oder falsch.
Jperelli
Wie @jperelli erwähnt hat, muss für die Sortierfunktion eine Zahl und kein Boolescher Wert zurückgegeben werden (und angesichts der Tatsache, dass es drei mögliche Zustände gibt, die oben und unten gleich sind, ist dies für eine stabile Sortierung erforderlich). Wie Ihre Antwort sagt, funktioniert es nicht. a-bsollte stattdessen verwendet werden. (Sie können Lust bekommen und eine machen Number(a>b)-0.5, aber das ist immer noch keine stabile Sorte).
ecc521