2012-08-01 20 views
22

Gibt es bessere Möglichkeiten, zwei verwandte Listen zufällig zu mischen, ohne ihre Korrespondenz in der anderen Liste zu unterbrechen? Ich habe verwandte Fragen in numpy.array und c# gefunden, aber nicht genau die gleiche.Bessere Möglichkeit, zwei verwandte Listen zu mischen

Als erster Versuch, ein einfacher zip Trick tun:

import random 
a = [[1, 2], [3, 4], [5, 6], [7, 8], [9, 10]] 
b = [2, 4, 6, 8, 10] 
c = zip(a, b) 
random.shuffle(c) 
a = [e[0] for e in c] 
b = [e[1] for e in c] 
print a 
print b 

Es wird die Ausgabe erhalten:

[[1, 2], [7, 8], [3, 4], [5, 6], [9, 10]] 
[2, 8, 4, 6, 10] 

Nur finde es ein wenig umständlich. Und es braucht auch eine zusätzliche Liste.

+5

Sie 'zip' können die Listen auch entpacken:' a, b = zip (* c) ' – mgilson

+3

ich auch ein Programm im Allgemeinen nicht empfehlen würde, Design, wo Sie eine Reihe von parallelen Listen halten müssen. Behalte einfach 1 Liste. Erstellen Sie eine Art von Klasse oder etwas, um Ihre Daten zu vereinheitlichen. – mgilson

+0

Wenn man solche Arbeit von 'numpy' machen will, hier ist eine gute Lösung: http: //stackoverflow.com/questions/4601373/better-way-to-shuffle-two-numpy-arrays-in-unison – Mithril

Antwort

35

Angesichts der in der Frage gezeigten Beziehung werde ich annehmen, dass die Listen die gleiche Länge haben und dass list1[i]list2[i] für jeden Index i entspricht. Mit dieser Annahme vorhanden, ist die Listen schlurfen so einfach wie das Mischen der Indizes:

from random import shuffle 
# Given list1 and list2 
list1_shuf = [] 
list2_shuf = [] 
index_shuf = range(len(list1)) 
shuffle(index_shuf) 
for i in index_shuf: 
    list1_shuf.append(list1[i]) 
    list2_shuf.append(list2[i]) 
+9

As ein Fan von Listen-Comprehensions: list1_shuf = [list1 [i] für i in index_shuf] –

+1

@kojiro: ist egal: n * append_ops + n * append_ops = n * (append_ops + append_ops) = 2 * n * append_ops – Lazik

5

Wenn Sie dies oft zu tun haben, könnten Sie ein Dereferenzierungsebene Erwägung ziehen, indem sie eine Liste von Indizes schlurfen.

Python 2.6.6 (r266:84297, Aug 24 2010, 18:13:38) [MSC v.1500 64 bit (AMD64)] on 
win32 
Type "help", "copyright", "credits" or "license" for more information. 
>>> import random 
>>> a = [[1, 2], [3, 4], [5, 6], [7, 8], [9, 10]] 
>>> b = [2, 4, 6, 8, 10] 
>>> indexes = range(len(a)) 
>>> indexes 
[0, 1, 2, 3, 4] 
>>> random.shuffle(indexes) 
>>> indexes 
[4, 1, 2, 0, 3] 
>>> for index in indexes: 
...  print a[index], b[index] 
... 
[9, 10] 10 
[3, 4] 4 
[5, 6] 6 
[1, 2] 2 
[7, 8] 8 
0

Ich bin mir nicht sicher, ob ich hier etwas fehlt bin, aber es sieht aus wie Sie gerade 1 der Listen schlurfend und das andere ist neu angeordnet, um die Reihenfolge der ersten Liste übereinstimmen. Was Sie haben, ist der beste Weg, dies zu tun, ohne es komplizierter zu machen. Wenn Sie die komplizierte Route gehen möchten, können Sie einfach eine Liste mischen und die nicht gemischte Liste verwenden, um in der gemischten Liste nachzusehen und sie auf diese Weise neu anzuordnen. Am Ende haben Sie das gleiche Ergebnis, mit dem Sie begonnen haben. Warum ist das Erstellen einer dritten Liste ein Problem? Wenn Sie die Listen wirklich wiederverwenden möchten, können Sie die Liste b einfach durch die für die Liste c verwendete ersetzen und sie später wieder auf a und b aufteilen.

1

Eine schnelle Antwort mit numpy finden Sie in here:
Sie

p = numpy.random.permutation(len(a)) 

verwenden können, um eine neue Liste von Indizes für beide Listen zu erstellen und sie neu zu ordnen verwenden.

In Ihrem Szenario:

In [61]: a = [[1, 2], [3, 4], [5, 6], [7, 8], [9, 10]] 
In [62]: b = [2, 4, 6, 8, 10] 
In [63]: import numpy as np 
In [64]: a_ar, b_ar = np.array(a), np.array(b) 
In [65]: p = np.random.permutation(len(a)) 
In [66]: a, b = a_ar[p].tolist(), b_ar[p].tolist() 
In [68]: a 
Out[68]: [[3, 4], [7, 8], [5, 6], [1, 2], [9, 10]] 
In [69]: b 
Out[69]: [4, 8, 6, 2, 10] 
14

Wenn Sie bereit sind, ein paar Pakete zu installieren:

Req: NumPy (> = 1.6.1), SciPy (> = 0.9).

pip installieren -U Scikit-Learn

from sklearn.utils import shuffle 
list_1, list_2 = shuffle(list_1, list_2) 
Verwandte Themen