¿hay alguna opción que no mute la matriz original pero devuelva una nueva matriz aleatoria?
Charlie Parker el
@Charlie Sería bueno hacer una pregunta por separado. (Tal vez alguien más ya lo ha preguntado.)
David Z
13
Irónicamente, esta página es el éxito principal en Google cuando busqué "python shuffle array"
Joshua Huber
2
@Charlie personas Google estas preguntas para que puedan encontrar respuestas a ellos en lugares como desbordamiento de pila. Mientras no sea un duplicado, no hay nada de malo en hacer que el desbordamiento de pila sea una opción como recurso
Matt
@javadba Eso fue en realidad una respuesta a la primera pregunta. No hay nada de malo en hacer preguntas sobre el desbordamiento de la pila, incluso si se puede encontrar excavando en Google. Permite que las personas futuras encuentren la respuesta en stackoverflow cuando hacen su propia excavación.
¿hay alguna opción que no mute la matriz original pero devuelva una nueva matriz aleatoria?
Charlie Parker el
36
Una forma alternativa de hacer esto usando sklearn
from sklearn.utils import shuffle
X=[1,2,3]
y =['one','two','three']
X, y = shuffle(X, y, random_state=0)print(X)print(y)
Salida:
[2,1,3]['two','one','three']
Ventaja: puede aleatorizar múltiples matrices simultáneamente sin interrumpir el mapeo. Y 'random_state' puede controlar la combinación para un comportamiento reproducible.
Gracias, es muy útil barajar dos matrices a la vez.
Dmitry
1
Estaba buscando esto, TNX!
NO
2
esto es más completo (y a menudo más útil) que la respuesta aceptada
javadba
21
Las otras respuestas son las más fáciles, sin embargo, es un poco molesto que el random.shufflemétodo en realidad no devuelva nada, simplemente clasifica la lista dada. Si desea encadenar llamadas o simplemente poder declarar una matriz aleatoria en una línea, puede hacer lo siguiente:
import random
def my_shuffle(array):
random.shuffle(array)return array
Entonces puedes hacer líneas como:
for suit in my_shuffle(['hearts','spades','clubs','diamonds']):
No devuelve nada específicamente porque está tratando de recordarle que funciona alterando la entrada en su lugar. (Esto puede ahorrar memoria). Su función también altera su entrada.
John Y
2
Supongo que es una cosa de estilo. Personalmente, prefiero el hecho de que puedo escribir una sola línea para lograr lo que de otro modo tomaría un par. Me parece extraño que un lenguaje que tiene como objetivo permitir que los programas sean lo más cortos posible no tiende a devolver el objeto pasado en estos casos. Como altera la entrada en su lugar, puede reemplazar una llamada a random.shuffle para una llamada a esta versión sin problemas.
Mark Rhodes
12
Python en realidad no pretende ser lo más breve posible. Python tiene como objetivo equilibrar la legibilidad con la expresividad. Resulta que es bastante breve, principalmente porque es un lenguaje de muy alto nivel. Propios muebles empotrados de Python normalmente (no siempre) se esfuerzan por cualquiera ser "functionlike" (devolver un valor, pero no tienen efectos secundarios) o ser "procedurelike" (operan a través de efectos secundarios, y no devuelven nada). Esto va de la mano con la distinción bastante estricta de Python entre declaraciones y expresiones.
John Y
Agradable. Sugiero cambiarle el nombre a my_shuffle para ver la diferencia en el código de inmediato.
Jabba
Tal vez, pero esto podría ser una optimización prematura (podría ser útil, pero la necesidad de barajar no requiere explícitamente la necesidad de devolver la matriz). Además, shuffle (array) seguido de algún uso de shuffle solo sería 2 líneas en lugar de 3 + n (veces el uso), aunque supongo que sería un ahorro si lo usa muchas veces. Aquí hay un gran video que analiza este tipo de cosas (por ejemplo, requisitos fantasmas y optimización prematura) - pyvideo.org/video/880/stop-writing-classes
Aaron Newton
12
Cuando se trata de listas regulares de Python, random.shuffle()hará el trabajo tal como lo muestran las respuestas anteriores.
Pero cuando se trata de ndarray( numpy.array), random.shuffleparece romper el original ndarray. Aquí hay un ejemplo:
import random
import numpy as np
import numpy.random
a = np.array([1,2,3,4,5,6])
a.shape =(3,2)print a
random.shuffle(a)# a will definitely be destroyedprint a
Solo usa: np.random.shuffle(a)
Al igual que random.shuffle, np.random.shufflebaraja la matriz en el lugar.
¿Esto crea un nuevo elemento aleatorio para cada elemento de la matriz?
javadba
@javadba No, esto simplemente ordena una matriz por índice aleatorio que terminará barajando la matriz
Trinh Hoang Nhu
1
Lo siento, tal vez no estaba claro, no quise decir que arrayquise decir el Randomelemento: es decir, en lambdael random.random()podría estar generando una nueva Randominstancia de clase cada vez. No estoy realmente seguro: en javaesta sería la forma incorrecta de hacerlo: debe crear un Random rng = Random()y luego invocar el rng.nextGaussian(). Pero no estoy seguro de cómo random.random()funciona Python
javadba
1
Si bien su código puede corregirse como respuesta, pero al elaborar lo que hace su código, puede mejorar la calidad de su respuesta. Consulte el artículo: ¿Cómo escribo una buena respuesta?
LuFFy
1
Además de las respuestas anteriores, me gustaría presentar otra función.
numpy.random.shuffleasí como random.shufflerealizar barajar en el lugar. Sin embargo, si desea devolver una matriz aleatoria numpy.random.permutationes la función a utilizar.
sí, devuelve Ninguno, pero la matriz está modificada, si realmente desea devolver algo, entonces haga esta importación aleatoria def shuffle (arr): random.shuffle (arr) return arr
user781903
0
# arr = numpy array to shuffledef shuffle(arr):
a = numpy.arange(len(arr))
b = numpy.empty(1)for i in range(len(arr)):
sel = numpy.random.random_integers(0, high=len(a)-1, size=1)
b = numpy.append(b, a[sel])
a = numpy.delete(a, sel)
b = b[1:].astype(int)return arr[b]
Tenga en cuenta que random.shuffle()no debe usarse en matrices multidimensionales, ya que provoca repeticiones.
Imagine que desea barajar una matriz a lo largo de su primera dimensión, podemos crear el siguiente ejemplo de prueba,
import numpy as np
x = np.zeros((10,2,3))for i in range(10):
x[i,...]= i*np.ones((2,3))
de modo que a lo largo del primer eje, el elemento i-ésimo corresponde a una matriz de 2x3 donde todos los elementos son iguales a i.
Si utilizamos la función aleatoria correcta para matrices multidimensionales, es decir np.random.shuffle(x), la matriz se barajará a lo largo del primer eje según se desee. Sin embargo, el uso random.shuffle(x)causará repeticiones. Puede verificar esto ejecutando len(np.unique(x))después de barajar, lo que le da 10 (como se esperaba) con np.random.shuffle()solo alrededor de 5 cuando lo usa random.shuffle().
new_array = random.sample( array, len(array) )
.Respuestas:
fuente
fuente
Una forma alternativa de hacer esto usando sklearn
Salida:
Ventaja: puede aleatorizar múltiples matrices simultáneamente sin interrumpir el mapeo. Y 'random_state' puede controlar la combinación para un comportamiento reproducible.
fuente
Las otras respuestas son las más fáciles, sin embargo, es un poco molesto que el
random.shuffle
método en realidad no devuelva nada, simplemente clasifica la lista dada. Si desea encadenar llamadas o simplemente poder declarar una matriz aleatoria en una línea, puede hacer lo siguiente:Entonces puedes hacer líneas como:
fuente
Cuando se trata de listas regulares de Python,
random.shuffle()
hará el trabajo tal como lo muestran las respuestas anteriores.Pero cuando se trata de
ndarray
(numpy.array
),random.shuffle
parece romper el originalndarray
. Aquí hay un ejemplo:Solo usa:
np.random.shuffle(a)
Al igual que
random.shuffle
,np.random.shuffle
baraja la matriz en el lugar.fuente
En caso de que desee una nueva matriz, puede usar
sample
:fuente
Puede ordenar su matriz con clave aleatoria
la clave solo se lee una vez, por lo que comparar el elemento durante la clasificación sigue siendo eficiente.
pero parece que
random.shuffle(array)
será más rápido ya que está escrito en Cfuente
array
quise decir elRandom
elemento: es decir, enlambda
elrandom.random()
podría estar generando una nuevaRandom
instancia de clase cada vez. No estoy realmente seguro: enjava
esta sería la forma incorrecta de hacerlo: debe crear unRandom rng = Random()
y luego invocar elrng.nextGaussian()
. Pero no estoy seguro de cómorandom.random()
funciona PythonAdemás de las respuestas anteriores, me gustaría presentar otra función.
numpy.random.shuffle
así comorandom.shuffle
realizar barajar en el lugar. Sin embargo, si desea devolver una matriz aleatorianumpy.random.permutation
es la función a utilizar.fuente
No sé si lo usé,
random.shuffle()
pero me devuelve 'Ninguno', así que escribí esto, podría ser útil para alguienfuente
fuente
Tenga en cuenta que
random.shuffle()
no debe usarse en matrices multidimensionales, ya que provoca repeticiones.Imagine que desea barajar una matriz a lo largo de su primera dimensión, podemos crear el siguiente ejemplo de prueba,
de modo que a lo largo del primer eje, el elemento i-ésimo corresponde a una matriz de 2x3 donde todos los elementos son iguales a i.
Si utilizamos la función aleatoria correcta para matrices multidimensionales, es decir
np.random.shuffle(x)
, la matriz se barajará a lo largo del primer eje según se desee. Sin embargo, el usorandom.shuffle(x)
causará repeticiones. Puede verificar esto ejecutandolen(np.unique(x))
después de barajar, lo que le da 10 (como se esperaba) connp.random.shuffle()
solo alrededor de 5 cuando lo usarandom.shuffle()
.fuente