Cómo generar números aleatorios en Java
⚡ Resumen inteligente
Números aleatorios en Java Provienen de cuatro opciones relacionadas de la biblioteca estándar: la clase Random, Math.random, ThreadLocalRandom y SecureRandom, cada una de las cuales ofrece una combinación diferente de velocidad, seguridad de subprocesos y solidez criptográfica para aplicaciones reales.

Los números aleatorios aparecen en todas partes Java, desde datos de pruebas unitarias y juegos de dados hasta fichas de sesión y mazos barajados. Este tutorial explica cómo generar números aleatorios en Java Utilizar todas las opciones de la biblioteca estándar y cómo elegir la más adecuada para cada tarea.
Generar números aleatorios en Java
El Java La biblioteca estándar ofrece cuatro formas comunes de generar un número aleatorio:
java.util.Randomes la clase de propósito general. Produce valores booleanos, enteros, largos, flotantes y dobles a través de métodos comonextInt,nextLong, ynextDouble.Math.randomes una función auxiliar estática que devuelve un valor double entre 0.0 (inclusive) y 1.0 (exclusivo) utilizando una función compartidaRandominternamente.ThreadLocalRandominjava.util.concurrentCada hilo tiene su propio generador, por lo que varios hilos no compiten por una misma instancia.SecureRandominjava.securityGenera números pseudoaleatorios criptográficamente seguros para contraseñas, identificadores de sesión y claves.
Las secciones siguientes muestran cómo generar diez números aleatorios con cada método.
Ejemplo: Generar un número aleatorio usando Java Clase aleatoria
El primer ejemplo utiliza java.util.Random para producir diez números enteros en el rango de 0 a 99 inclusive:
import java.util.Random; public class RandomNumbers { public static void main(String[] args) { Random objGenerator = new Random(); for (int iCount = 0; iCount < 10; iCount++) { int randomNumber = objGenerator.nextInt(100); System.out.println("Random No : " + randomNumber); } } }
Salida:
Random No : 17 Random No : 57 Random No : 73 Random No : 48 Random No : 68 Random No : 86 Random No : 34 Random No : 97 Random No : 73 Random No : 18
Una instancia de Random se crea como objGenerator. La función de nextInt(int bound) El método devuelve un valor entre 0 (inclusive) y el límite proporcionado (exclusivo), por lo que nextInt(100) produce valores de 0 a 99. Para que la secuencia sea reproducible, pase una semilla al constructor, por ejemplo new Random(42); la misma semilla siempre produce la misma secuencia, lo cual es útil en pruebas y simulaciones.
Ejemplo: Uso Java Matemáticas aleatorias
Para generar diez valores aleatorios en el rango de 0.0 a 1.0, llame a la función estática. Math.random método dentro de un loopsEsta es la forma más rápida de obtener un número doble aleatorio sin crear un objeto generador:
public class DemoRandom { public static void main(String[] args) { for (int xCount = 0; xCount < 10; xCount++) { System.out.println(Math.random()); } } }
Salida:
0.46518450373334297 0.14859851177803485 0.5628391820492477 0.6323378498048606 0.1740198445692248 0.9140544122258946 0.9167350036262347 0.49251219841030147 0.7426056725722353 0.2039418871298877
Bajo el capó, Math.random crea un único estático Random en el primer uso y llamadas nextDouble En ello. Ese generador compartido único está bien para demostraciones, pero se convierte en un cuello de botella bajo una carga multihilo pesada, tema que se aborda en las siguientes secciones.
Generar un número aleatorio en un rango personalizado.
Los programas reales suelen necesitar un valor aleatorio dentro de un rango específico, como un número entero entre 1 y 6 para una tirada de dados o un número decimal entre 10.0 y 20.0 para una simulación. Dos patrones cubren casi todos los casos.
Número entero aleatorio entre min y max (inclusive):
import java.util.Random; public class RangeDemo { public static void main(String[] args) { Random rnd = new Random(); int min = 1; int max = 6; // nextInt(max - min + 1) returns 0..(max-min), then shift by min int dice = rnd.nextInt(max - min + 1) + min; System.out.println("Dice roll : " + dice); } }
Número doble aleatorio entre mínimo y máximo:
double min = 10.0; double max = 20.0; double value = min + (max - min) * Math.random(); System.out.println("Value : " + value);
Ambos patrones funcionan tomando un valor del rango nativo del generador, escalándolo al ancho del rango objetivo y desplazándolo hacia arriba en el mínimo. Si estás en Java 8 o posterior, el mismo resultado está disponible a través de la versión más reciente. ints, longs, y doubles métodos de flujo en Random, Por ejemplo rnd.ints(10, 1, 7).forEach(System.out::println) para diez tiradas de dados.
ThreadLocalRandom para multihilo Code
Un único compartido Random Es seguro para subprocesos, pero lento en situaciones de contención porque cada subproceso tiene que sincronizarse con la misma semilla interna. ThreadLocalRandom, añadido en Java 7 y viviendo en java.util.concurrentEsto le da a cada hilo su propio generador, por lo que no hay contención de bloqueos.
import java.util.concurrent.ThreadLocalRandom; public class ThreadLocalDemo { public static void main(String[] args) { // random int in [1, 100] int i = ThreadLocalRandom.current().nextInt(1, 101); // random long in [1000, 5000] long l = ThreadLocalRandom.current().nextLong(1000L, 5001L); // random double in [0.0, 1.0) double d = ThreadLocalRandom.current().nextDouble(); System.out.println(i + " " + l + " " + d); } }
Usar ThreadLocalRandom.current() dentro de los subprocesos de trabajo, flujos paralelos y cualquier tarea concurrente. Tenga en cuenta que setSeed tiros UnsupportedOperationException, por lo que no se admite la inicialización para la reproducibilidad; si necesita una inicialización fija, siga con la inicialización simple. Random.
SecureRandom para generación aleatoria sensible a la seguridad Numbers
Instancias de Random y ThreadLocalRandom no son criptográficamente seguros. Con unas pocas muestras de salida, un atacante puede reconstruir el estado interno y predecir valores futuros. Para contraseñas, tokens de sesión, valores de sal y claves criptográficas, utilice java.security.SecureRandom En cambio, extrae material semilla del conjunto de entropía del sistema operativo y produce valores que se resisten a la predicción.
import java.security.SecureRandom; public class SecureDemo { public static void main(String[] args) { SecureRandom secure = new SecureRandom(); byte[] token = new byte[16]; secure.nextBytes(token); // 128-bit random token int otp = secure.nextInt(1_000_000); // 6-digit one-time code System.out.println("OTP : " + String.format("%06d", otp)); } }
SecureRandom es más lento que Random Porque utiliza algoritmos más robustos y datos de partida más completos. Resérvelo para tareas de seguridad y utilice los generadores más rápidos para juegos, simulaciones y datos de prueba.
