Angenommen, ich habe zwei Listen:
list1 = [3, 2, 4, 1, 1]
list2 = ['three', 'two', 'four', 'one', 'one2']
Wenn ich laufe list1.sort()
, wird es sortiert, [1,1,2,3,4]
aber gibt es auch eine Möglichkeit, list2
synchron zu werden (also kann ich sagen, dass das Element dazu 4
gehört 'three'
)? Die erwartete Ausgabe wäre also:
list1 = [1, 1, 2, 3, 4]
list2 = ['one', 'one2', 'two', 'three', 'four']
Mein Problem ist, dass ich ein ziemlich komplexes Programm habe, das gut mit Listen funktioniert, aber ich muss anfangen, auf einige Daten zu verweisen. Ich weiß, dass dies eine perfekte Situation für Wörterbücher ist, aber ich versuche, Wörterbücher in meiner Verarbeitung zu vermeiden, da ich die Schlüsselwerte sortieren muss (wenn ich Wörterbücher verwenden muss, weiß ich, wie man sie verwendet).
Grundsätzlich liegt die Natur dieses Programms darin, dass die Daten in zufälliger Reihenfolge (wie oben) vorliegen. Ich muss sie sortieren, verarbeiten und dann die Ergebnisse senden (die Reihenfolge spielt keine Rolle, aber die Benutzer müssen wissen, welches Ergebnis zu welchem gehört Schlüssel). Ich habe darüber nachgedacht, es zuerst in ein Wörterbuch aufzunehmen und dann die Liste eins zu sortieren, aber ich hätte keine Möglichkeit, Elemente mit demselben Wert zu unterscheiden, wenn die Reihenfolge nicht eingehalten wird (dies kann sich auf die Übermittlung der Ergebnisse an die Benutzer auswirken). Wenn ich die Listen habe, würde ich im Idealfall lieber einen Weg finden, beide Listen zusammen zu sortieren. Ist das möglich?
Antworten:
Ein klassischer Ansatz für dieses Problem ist die Verwendung der Redewendung "Dekorieren, Sortieren, Nichtdekorieren", die mit der in Python integrierten
zip
Funktion besonders einfach ist :Dies sind natürlich keine Listen mehr, aber das kann leicht behoben werden, wenn es darauf ankommt:
Es ist erwähnenswert, dass das oben Genannte Geschwindigkeit für Knappheit opfern kann; Die In-Place-Version, die 3 Zeilen belegt, ist auf meinem Computer für kleine Listen etwas schneller:
Andererseits könnte bei größeren Listen die einzeilige Version schneller sein:
Wie Quantum7 hervorhebt, ist der Vorschlag von JSF noch etwas schneller, wird aber wahrscheinlich immer nur ein bisschen schneller sein, da Python intern für alle schlüsselbasierten Sortierungen dieselbe DSU -Sprache verwendet. Es passiert nur ein bisschen näher am Bare Metal. (Dies zeigt, wie gut die
zip
Routinen optimiert sind!)Ich denke, der
zip
basierte Ansatz ist flexibler und etwas lesbarer, deshalb bevorzuge ich ihn.quelle
*
zip(*x)
hat die interessante Eigenschaft, dass es seine eigene Umkehrung ist: gibtl = [(1, 2), (3, 4)]; list(zip(*zip(*l))) == l
zurückTrue
. Es ist effektiv ein Umsetzungsoperator.zip()
Dies ist für sich genommen der gleiche Operator, setzt jedoch voraus, dass Sie die Eingabesequenz manuell entpackt haben.Sie können Indizes mit Werten als Schlüssel sortieren:
So erhalten Sie sortierte Listen mit sortierten Indizes:
In Ihrem Fall sollten Sie nicht haben
list1
,list2
sondern eine einzelne Liste von Paaren:Es ist einfach zu erstellen; In Python ist es einfach zu sortieren:
Nur nach dem ersten Wert sortieren:
quelle
list()
herum,map()
wenn Sie diesen Code in Python 3 verwendensorted_list1 = list(map(list1.__getitem__, indexes))
könnte man es tunsorted_list1 = [list1[i] for i in indexes]
.Ich habe die Antwort von senderle lange verwendet, bis ich sie entdeckte
np.argsort
. So funktioniert es.Ich finde diese Lösung intuitiver und sie funktioniert sehr gut. Die Leistung:
Obwohl
np.argsort
es nicht das schnellste ist, finde ich es einfacher zu bedienen.quelle
TypeError: only integer arrays with one element can be converted to an index
angezeigt : (Python 2.7.6, numpy 1.8.2). Um dies zu beheben, müssen list1 und list2 als numpy-Arrays deklariert werden.np.argsort
nicht zu versuchen,np.array
intern zu konvertieren .Schwartzsche Transformation . Die integrierte Python-Sortierung ist stabil, sodass die beiden
1
keine Probleme verursachen.quelle
Wie wäre es mit:
quelle
Sie können die Funktionen
zip()
undsort()
verwenden, um dies zu erreichen:Hoffe das hilft
quelle
Sie können das Schlüsselargument in der Methode sorted () verwenden, es sei denn, Sie haben zwei gleiche Werte in list2.
Der Code ist unten angegeben:
Es sortiert list2 nach den entsprechenden Werten in list1, stellt jedoch sicher, dass dabei keine zwei Werte in list2 als gleich ausgewertet werden, da die Funktion list.index () den ersten Wert angibt
quelle
Eine Möglichkeit besteht darin, zu verfolgen, wohin jeder Index führt, indem die Identität [0,1,2, .. n] sortiert wird.
Dies funktioniert für eine beliebige Anzahl von Listen.
Bewegen Sie dann jeden Gegenstand an seine Position. Am besten verwenden Sie Spleiße.
Beachten Sie, dass wir die Listen hätten iterieren können, ohne sie zu sortieren:
quelle
Wenn Sie numpy verwenden, können
np.argsort
Sie die sortierten Indizes abrufen und diese Indizes auf die Liste anwenden. Dies funktioniert für eine beliebige Anzahl von Listen, die Sie sortieren möchten.quelle
eine algorithmische Lösung:
Ausgänge:
->
Ausgabegeschwindigkeit:0.2s
quelle
Ein anderer Ansatz zum Beibehalten der Reihenfolge einer Zeichenfolgenliste beim Sortieren nach einer anderen Liste lautet wie folgt:
Ausgabe
quelle
Ich möchte die Antwort von open jfs erweitern , die für mein Problem sehr gut funktioniert hat: Sortieren von zwei Listen nach einer dritten, dekorierten Liste :
Wir können unsere dekorierte Liste auf jede Art und Weise erstellen, aber in diesem Fall erstellen wir sie aus den Elementen einer der beiden ursprünglichen Listen, die wir sortieren möchten:
Jetzt können wir die Lösung von jfs anwenden , um unsere beiden Listen nach der dritten zu sortieren
Edit: Hey Leute, ich habe einen Blockpost darüber gemacht, schau es dir an, wenn du Lust dazu hast :) 🐍🐍🐍
quelle
quelle