¿Cómo puedo generar algunos números aleatorios únicos entre 1 y 100 usando JavaScript?
javascript
random
integer
numbers
punteado
fuente
fuente
Respuestas:
Por ejemplo: para generar 8 números aleatorios únicos y almacenarlos en una matriz, simplemente puede hacer esto:
fuente
Returns a random number between 0 (inclusive) and 1 (exclusive)
. Sithe Math.random()
accidentalmente devuelve 0,Math.ceil(0)
también es 0, aunque la probabilidad es baja.fuente
randlines file | head -10
.Genere la permutación de 100 números y luego elija en serie.
Utilice el algoritmo Knuth Shuffle (también conocido como Fisher-Yates shuffle) .
JavaScript:
CÓDIGO COPIADO DESDE LINK.
EDITAR :
Código mejorado:
Problema potencial:
Supongamos que tenemos una matriz de 100 números {por ejemplo, [1,2,3 ... 100]} y dejamos de intercambiar después de 8 intercambios; entonces la mayoría de las veces la matriz se verá como {1,2,3,76,5,6,7,8, ... los números aquí se mezclarán ... 10}.
Porque todos los números se intercambiarán con una probabilidad de 1/100, así que prob. de intercambiar los primeros 8 números es 8/100 mientras que prob. de intercambiar otros 92 es 92/100.
Pero si ejecutamos el algoritmo para una matriz completa, entonces estamos seguros de que (casi) todas las entradas se intercambian.
De lo contrario nos enfrentamos a una pregunta: ¿qué 8 números elegir?
fuente
Solución JS moderna usando Set (y caso promedio O (n))
fuente
Math.floor(Math.random()*100) + 1
Set
en JS! Sin embargo, ¿no causaría esta solución una generación innecesaria de números hasta que uno cumpla con el requisito de unicidad, especialmente en las últimas iteraciones, si 8 estuviera más cerca de 100? Por lo tanto, creo que prefiero la respuesta también elegante asort
continuación.Las técnicas anteriores son buenas si desea evitar una biblioteca, pero dependiendo de si estaría bien con una biblioteca, le sugiero que consulte Chance para generar material aleatorio en JavaScript.
Específicamente para resolver su pregunta, usar Chance es tan fácil como:
Descargo de responsabilidad, como autor de Chance, soy un poco parcial;)
fuente
var codes = chance.unique(chance.string, 8)
Si necesitas los códigos extraídos de un grupo de caracteres en particular, puedes especificarlo de esta manera:chance.unique(chance.string, 8, {pool: "abcd1234"})
donde abcd1234 puede ser cualquier carácter que quieras en el grupo. Ver chancejs.com/#stringchance.string({ length: 8 })
y si solo quieres que aparezcan ciertos caracteres en esa cadena,chance.string({ pool: 'abcd1234', length: 8 })
que devolvería una cadena aleatoria de 8 caracteres de los caracteres abcd1234, por ejemplo, "2c2c44bc" o "331141cc"Para evitar cambios largos y poco fiables, haría lo siguiente ...
Voila, no hay números repetidos.
Puedo publicar algún código real más tarde, si alguien está interesado.
Editar: Probablemente sea la racha competitiva en mí, pero, habiendo visto la publicación de @Alsciende, no pude resistirme a publicar el código que prometí.
fuente
Otro enfoque es generar una matriz de 100 elementos con números ascendentes y ordenarlos al azar. En realidad, esto conduce a un fragmento muy corto y (en mi opinión) simple.
fuente
sort
esté bien implementado, que estoy seguro).Yo haría esto:
fuente
Esta es una función muy genérica que he escrito para generar enteros aleatorios únicos / no únicos para una matriz. Suponga que el último parámetro es verdadero en este escenario para esta respuesta.
Aquí el 'tempObj' es un obj muy útil ya que cada número aleatorio generado verificará directamente en este tempObj si esa clave ya existe, si no, entonces reducimos la i en uno ya que necesitamos 1 ejecución adicional ya que el número aleatorio actual ya existe .
En su caso, ejecute lo siguiente
Eso es todo.
fuente
min = (min) ? min : 1,
siempre devolverá 1. (por lo que nunca se seleccionará 0)Mezclar los números del 1 al 100 es la estrategia básica correcta, pero si solo necesita 8 números mezclados, no es necesario mezclar los 100 números.
No conozco muy bien Javascript, pero creo que es fácil crear una matriz de 100 nulos rápidamente. Luego, durante 8 rondas, intercambia el n-ésimo elemento de la matriz (n comenzando en 0) con un elemento seleccionado al azar de n + 1 a 99. Por supuesto, cualquier elemento que aún no se haya completado significa que el elemento realmente habría sido el índice original más 1, por lo que es trivial factorizar. Cuando haya terminado con las 8 rondas, los primeros 8 elementos de su matriz tendrán sus 8 números mezclados.
fuente
más corto que otras respuestas que he visto
fuente
El mismo algoritmo de permutación que The Machine Charmer, pero con una implementación prototipada. Se adapta mejor a una gran cantidad de picos. Utiliza la asignación de desestructuración js 1.7 si está disponible.
Editar: Otra propuesta, más adecuada para una pequeña cantidad de selecciones, basada en la respuesta de belugabob. Para garantizar la unicidad, eliminamos los números seleccionados de la matriz.
fuente
para matrices con agujeros como este
[,2,,4,,6,7,,]
porque mi problema era llenar estos agujeros. Así que lo modifiqué según mi necesidad :)la siguiente solución modificada funcionó para mí :)
fuente
La mejor respuesta anterior es la respuesta de
sje397
. Obtendrá los mejores números aleatorios que pueda obtener, lo más rápido posible.Mi solución es muy similar a su solución. Sin embargo, a veces quieres los números aleatorios en orden aleatorio, y es por eso que decidí publicar una respuesta. Además, proporciono una función general.
fuente
Aquí está mi versión ES6 que improvisé. Seguro que se puede consolidar un poco más.
fuente
¿Qué tal usar las propiedades del objeto como una tabla hash ? De esta manera, su mejor escenario es aleatorizar solo 8 veces. Solo sería efectivo si desea una pequeña parte del rango de números. También requiere mucha menos memoria que Fisher-Yates porque no tiene que asignar espacio para una matriz.
Luego descubrí que Object.keys (obj) es una característica de ECMAScript 5, por lo que lo anterior es prácticamente inútil en Internet en este momento. No temas, porque lo hice compatible con ECMAScript 3 agregando una función de teclas como esta.
fuente
fuente
si necesita más exclusivo, debe generar una matriz (1..100).
El código anterior es más rápido:
extractUniqueRandomArray (50) => [2, 79, 38, 59, 63, 42, 52, 22, 78, 50, 39, 77, 1, 88, 40, 23, 48, 84, 91, 49, 4, 54, 93, 36, 100, 82, 62, 41, 89, 12, 24, 31, 86, 92, 64, 75, 70, 61, 67, 98, 76, 80, 56, 90, 83, 44, 43, 47, 7, 53]
fuente
Añadiendo otra versión mejor del mismo código (respuesta aceptada) con la función indexOf de JavaScript 1.6. No es necesario recorrer toda la matriz cada vez que verifica el duplicado.
La versión anterior de Javascript aún puede usar la versión en la parte superior
PD: Intenté sugerir una actualización de la wiki pero fue rechazada. Sigo pensando que puede ser útil para otros.
fuente
Esta es mi solución personal:
Genera aleatoriamente 8 valores de matriz únicos (entre 0 y 7), luego los muestra usando un cuadro de alerta.
fuente
Creo que este método es diferente de los métodos dados en la mayoría de las respuestas, así que pensé que podría agregar una respuesta aquí (aunque la pregunta se hizo hace 4 años).
Generamos 100 números aleatorios y etiquetamos cada uno de ellos con números del 1 al 100. Luego clasificamos estos números aleatorios etiquetados y las etiquetas se mezclan aleatoriamente. Alternativamente, según sea necesario en esta pregunta, se podría eliminar simplemente encontrar los 8 primeros números aleatorios etiquetados. Encontrar los 8 elementos principales es más barato que ordenar toda la matriz.
Hay que señalar aquí que el algoritmo de clasificación influye en este algoritmo. Si el algoritmo de clasificación utilizado es estable, existe un ligero sesgo a favor de números más pequeños. Idealmente, querríamos que el algoritmo de clasificación fuera inestable y ni siquiera sesgado hacia la estabilidad (o inestabilidad) para producir una respuesta con una distribución de probabilidad perfectamente uniforme.
fuente
Esto puede manejar la generación de un número aleatorio ÚNICO de hasta 20 dígitos
JS
jsFiddle
fuente
Esta solución utiliza el hash, que es mucho más eficaz O (1) que comprobar si reside en la matriz. También tiene controles de seguridad adicionales. Espero eso ayude.
fuente
Implementar esto como un generador hace que sea bastante agradable trabajar con él. Tenga en cuenta que esta implementación difiere de las que requieren que la matriz de entrada completa se mezcle primero.
Elegí implementar
sample
de una manera que no mute la matriz de entrada, pero se podría argumentar fácilmente que una implementación mutante es favorable.Por ejemplo, es posible que la
shuffle
función desee mutar la matriz de entrada original. O tal vez desee tomar muestras de la misma entrada en varios momentos, actualizando la entrada cada vez.sample
ya no es una función pura debido a la mutación de entrada de la matriz, pero en ciertas circunstancias (como se demostró anteriormente) podría tener más sentido.Otra razón por la que elegí un generador en lugar de una función que solo devuelve una matriz es porque es posible que desee continuar muestreando hasta alguna condición específica.
Quizás quiero el primer número primo de una lista de 1.000.000 de números aleatorios.
Como estamos trabajando con un generador, esta tarea es trivial.
Esto muestreará continuamente 1 número aleatorio a la vez
x
, verificará si es primo y luego devolveráx
si lo es. Si la lista de números se agota antes de encontrar un primo,NaN
se devuelve.Nota:
Esta respuesta se compartió originalmente en otra pregunta que se cerró como un duplicado de esta. Debido a que es muy diferente de las otras soluciones proporcionadas aquí, he decidido compartirlo aquí también.
fuente
fuente
Usar a
Set
es la opción más rápida. Aquí hay una función genérica para obtener un aleatorio único que usa un generador de devolución de llamada. Ahora es rápido y reutilizable .fuente
Esta es una implementación de Fisher Yates / Durstenfeld Shuffle , pero sin la creación real de una matriz, lo que reduce la complejidad del espacio o la memoria necesaria, cuando el tamaño de selección es pequeño en comparación con la cantidad de elementos disponibles.
Para elegir 8 números de 100, no es necesario crear una matriz de 100 elementos.
Suponiendo que se crea una matriz,
rnd
) de 1 a 100rnd
Si no se crea una matriz, se puede usar un hashMap para recordar las posiciones intercambiadas reales. Cuando el segundo número aleatorio generado es igual al de los números generados anteriormente, el mapa proporciona el valor actual en esa posición en lugar del valor real.
fuente
Aquí hay un ejemplo de 5 números aleatorios tomados de un rango de 0 a 100 (tanto 0 como 100 incluidos) sin duplicación.
fuente
También puedes hacerlo con un trazador de líneas como este:
[...((add, set) => add(set, add))((set, add) => set.size < 8 ? add(set.add(Math.floor(Math.random()*100) + 1), add) : set, new Set())]
fuente