Como gerar inteiros aleatórios dentro de uma gama específica em Java?
Como posso gerar um valor aleatório {[[2]} num intervalo específico?
tentei o seguinte, mas aqueles não funcionam:
tentativa 1:
randomNum = minimum + (int)(Math.random() * maximum);
// Bug: `randomNum` can be bigger than `maximum`.
tentativa 2:
Random rn = new Random();
int n = maximum - minimum + 1;
int i = rn.nextInt() % n;
randomNum = minimum + i;
// Bug: `randomNum` can be smaller than `minimum`.
30 answers
Em Java 1, 7 ou mais tarde, a forma padrão de o fazer é a seguinte:
import java.util.concurrent.ThreadLocalRandom;
// nextInt is normally exclusive of the top value,
// so add 1 to make it inclusive
int randomNum = ThreadLocalRandom.current().nextInt(min, max + 1);
Ver o JavaDoc relevante . Esta abordagem tem a vantagem de não precisar inicializar explicitamente um java.util.Caso Aleatório , que pode ser uma fonte de confusão e erro se usado de forma inadequada.
No entanto, por outro lado, não há forma de definir explicitamente a semente, pelo que pode ser difícil reproduzir resultados em situações em que isso seja útil, tais como ensaios ou ensaios. a gravar estados do jogo ou semelhantes. Nessas situações, a técnica pré-Java 1.7 mostrada abaixo pode ser usada.Antes do Java 1.7 , a forma padrão de fazer isto é a seguinte:
import java.util.Random;
/**
* Returns a pseudo-random number between min and max, inclusive.
* The difference between min and max can be at most
* <code>Integer.MAX_VALUE - 1</code>.
*
* @param min Minimum value
* @param max Maximum value. Must be greater than min.
* @return Integer between min and max, inclusive.
* @see java.util.Random#nextInt(int)
*/
public static int randInt(int min, int max) {
// NOTE: This will (intentionally) not run as written so that folks
// copy-pasting have to think about how to initialize their
// Random instance. Initialization of the Random instance is outside
// the main scope of the question, but some decent options are to have
// a field that is initialized once and then re-used as needed or to
// use ThreadLocalRandom (if using at least Java 1.7).
//
// In particular, do NOT do 'Random rand = new Random()' here or you
// will get not very good / not very random results.
Random rand;
// nextInt is normally exclusive of the top value,
// so add 1 to make it inclusive
int randomNum = rand.nextInt((max - min) + 1) + min;
return randomNum;
}
Ver o JavaDoc relevante . Na prática, o java.util.A classe Random é muitas vezes preferível a java.idioma.Matematico.random().
Em particular, não há necessidade de reinventar a roda de geração de inteiros aleatórios quando há uma API simples dentro da norma biblioteca para realizar a tarefa.
Note que esta abordagem é mais tendenciosa e menos eficiente do que uma abordagem nextInt
, https://stackoverflow.com/a/738651/360211
Um padrão para realizar isto é:
Min + (int)(Math.random() * ((Max - Min) + 1))
The Java Math library function Math Math.random () gera um valor duplo no intervalo [0,1)
. Note que este intervalo não inclui o 1.
Para obter uma gama específica de valores em primeiro lugar, é necessário multiplicar-se pela magnitude da Gama de valores queres cobertura.
Math.random() * ( Max - Min )
Isto devolve um valor no intervalo [0,Max-Min)
, onde 'Max-Min' não está incluído.
Por exemplo, se quiser [5,10)
, precisa de cobrir cinco valores inteiros para usar
Math.random() * 5
Isto devolveria um valor na gama [0,5)
, onde 5 não está incluído.
Min + (Math.random() * (Max - Min))
Agora você vai ter um valor no intervalo [Min,Max)
. Seguinte o nosso exemplo, isso significa [5,10)
:
5 + (Math.random() * (10 - 5))
Mas, isto ainda não inclui Max
e estás a ter um valor duplo. A fim de obter o valor Max
incluído, você precisa adicionar 1 ao seu parâmetro de intervalo (Max - Min)
e, em seguida, truncar a parte decimal, lançando para um int. Isto é conseguido através de:
Min + (int)(Math.random() * ((Max - Min) + 1))
E aí está. Um valor inteiro aleatório no intervalo [Min,Max]
, ou pelo exemplo [5,10]
:
5 + (int)(Math.random() * ((10 - 5) + 1))
Utilizar:
Random ran = new Random();
int x = ran.nextInt(6) + 5;
O inteiro x
é agora o número aleatório que tem um resultado possível de 5-10
.
Utilizar:
minimum + rn.nextInt(maxValue - minvalue + 1)
Comjava-8 introduziram o método ints(int randomNumberOrigin, int randomNumberBound)
na Random
classe.
Por exemplo, se quiser gerar cinco inteiros aleatórios (ou um único) no intervalo [0, 10], basta fazer:
Random r = new Random();
int[] fiveRandomNumbers = r.ints(5, 0, 11).toArray();
int randomNumber = r.ints(1, 0, 11).findFirst().getAsInt();
O primeiro parâmetro indica apenas o tamanho do IntStream
gerado (que é o método sobrecarregado do que produz um IntStream
ilimitado).
public final class IntRandomNumberGenerator {
private PrimitiveIterator.OfInt randomIterator;
/**
* Initialize a new random number generator that generates
* random numbers in the range [min, max]
* @param min - the min value (inclusive)
* @param max - the max value (inclusive)
*/
public IntRandomNumberGenerator(int min, int max) {
randomIterator = new Random().ints(min, max + 1).iterator();
}
/**
* Returns a random number in the range (min, max)
* @return a random number in the range (min, max)
*/
public int nextInt() {
return randomIterator.nextInt();
}
}
Também o pode fazer pelos valores de double
e long
.
Pode editar o seu segundo exemplo de código para:
Random rn = new Random();
int range = maximum - minimum + 1;
int randomNum = rn.nextInt(range) + minimum;
Random rand = new Random();
randomNum = minimum + rand.nextInt((maximum - minimum) + 1);
Veja mais aqui para a implementação de Random
Equivalente ThreadLocalRandom da classe java.util.Random for multithreaded environment. Gerar um número aleatório é realizado localmente em cada um dos threads. Assim, temos um melhor desempenho reduzindo os conflitos.
int rand = ThreadLocalRandom.current().nextInt(x,y);
X, y - intervalos P. ex. (1,10)
A classe Math.Random
em Java é baseada em 0. Então, se escreveres algo assim:
Random rand = new Random();
int x = rand.nextInt(10);
x
será entre 0-9
inclusive.
Assim, dado o seguinte matriz de 25
itens, o código para gerar um número aleatório entre 0
(a base da matriz) e array.length
seria:
String[] i = new String[25];
Random rand = new Random();
int index = 0;
index = rand.nextInt( i.length );
Uma vez que i.length
vai voltar 25
, o nextInt( i.length )
vai devolver um número entre o intervalo de 0-24
. A outra opção está indo com Math.Random
que funciona na mesma forma.
index = (int) Math.floor(Math.random() * i.length);
Para uma melhor compreensão, confira o post do fórum intervalos aleatórios (archive.org).
-
rng.nextInt(n)
não consegue chegarInteger.MAX_VALUE
. -
(max - min)
pode causar transbordamento quando {[5] } for negativo.
Uma solução à prova de falhas devolveria os resultados correctos para qualquer min <= max
dentro do intervalo [Integer.MIN_VALUE
, Integer.MAX_VALUE
]. Considere a seguinte aplicação ingênua:
int nextIntInRange(int min, int max, Random rng) {
if (min > max) {
throw new IllegalArgumentException("Cannot draw random int from invalid range [" + min + ", " + max + "].");
}
int diff = max - min;
if (diff >= 0 && diff != Integer.MAX_VALUE) {
return (min + rng.nextInt(diff + 1));
}
int i;
do {
i = rng.nextInt();
} while (i < min || i > max);
return i;
}
Apesar de ineficiente, note que a probabilidade de sucesso no loop while
será sempre 50% ou mais.
Pergunto-me se algum dos métodos aleatórios de geração de números fornecidos por uma Matemática Apache Commons caberia na conta.
Por exemplo: RandomDataGenerator.nextInt
ou RandomDataGenerator.nextLong
int max = 10;
int min = 5;
int diff = max - min;
Random rn = new Random();
int i = rn.nextInt(diff + 1);
i += min;
System.out.print("The Random Number is " + i);
vamos entender isso...
Inicializar max com o valor mais elevado e min com o valor mais baixo.
Agora, precisamos determinar quantos valores possíveis podem ser obtidos. Por exemplo, seria:Então, a contagem disto seria máx. - min + 1.5, 6, 7, 8, 9, 10
I. e. 10 - 5 + 1 = 6
O número aleatório irá gerar um número entre 0-5.
I. e. 0, 1, 2, 3, 4, 5
Adicionar o valor min ao número aleatório produziria:
Por isso obtemos o alcance desejado.5, 6, 7, 8, 9, 10
rand.nextInt((max+1) - min) + min;
Aqui está uma classe útil para gerar aleatoriamente ints
num intervalo com qualquer combinação de limites inclusivos/exclusivos:
import java.util.Random;
public class RandomRange extends Random {
public int nextIncInc(int min, int max) {
return nextInt(max - min + 1) + min;
}
public int nextExcInc(int min, int max) {
return nextInt(max - min) + 1 + min;
}
public int nextExcExc(int min, int max) {
return nextInt(max - min - 1) + 1 + min;
}
public int nextIncExc(int min, int max) {
return nextInt(max - min) + min;
}
}
Gerar um número aleatório para a diferença de min e max usando o método nextint (n) e depois adicionar o número min ao resultado:
Random rn = new Random();
int result = rn.nextInt(max - min + 1) + min;
System.out.println(result);
Em caso de lançar um dado, seria um número aleatório entre 1 e 6( não entre 0 e 6), por isso:
face = 1 + randomNumbers.nextInt(6);
A partir do Java 7, você não deve mais usar
Random
. Para a maioria dos usos, o gerador de números aleatórios de escolha é agoraThreadLocalRandom
.
para piscinas de juntas de garfo e paralelas fluxos, utilizaçãoSplittableRandom
.
Joshua Bloch. Java Eficaz. Terceira Edição.
A partir de Java 8 ([14]} No caso das juntas de garfo e dos fluxos paralelos, o uso ([5]} que é geralmente mais rápido, tem uma melhor independência estatística e propriedades de uniformidade em comparação comRandom
.
Para gerar um aleatório int
no intervalo [0, 1_000]:
int n = new SplittableRandom().nextInt(0, 1_001);
Para gerar uma matriz aleatória int[100]
de valores no intervalo [0, 1_000]:
int[] a = new SplittableRandom().ints(100, 0, 1_001).parallel().toArray();
Para devolver um fluxo de valores aleatórios:
IntStream stream = new SplittableRandom().ints(100, 0, 1_001);
int random = minimum + Double.valueOf(Math.random()*(maximum-minimun)).intValue();
{[[2]} ou dar uma vista de olhos aos RandomUtils de Apache Commons.
Este método pode ser conveniente de utilizar:
Este método irá devolver um número aleatórioentre valor mínimo e máximo fornecido:
public static int getRandomNumberBetween(int min, int max) {
Random foo = new Random();
int randomNumber = foo.nextInt(max - min) + min;
if (randomNumber == min) {
// Since the random number is between the min and max values, simply add 1
return min + 1;
} else {
return randomNumber;
}
}
E este método irá devolver um número aleatóriode o valor min e o valor máximo fornecidos (de modo que o número gerado também pode ser o número min ou o número max):
public static int getRandomNumberFrom(int min, int max) {
Random foo = new Random();
int randomNumber = foo.nextInt((max + 1) - min) + min;
return randomNumber;
}
public static Random RANDOM = new Random(System.nanoTime());
public static final float random(final float pMin, final float pMax) {
return pMin + RANDOM.nextFloat() * (pMax - pMin);
}
Encontrei este exemplo gera números aleatórios :
Este exemplo gera inteiros aleatórios num intervalo específico.
import java.util.Random;
/** Generate random integers in a certain range. */
public final class RandomRange {
public static final void main(String... aArgs){
log("Generating random integers in the range 1..10.");
int START = 1;
int END = 10;
Random random = new Random();
for (int idx = 1; idx <= 10; ++idx){
showRandomInteger(START, END, random);
}
log("Done.");
}
private static void showRandomInteger(int aStart, int aEnd, Random aRandom){
if ( aStart > aEnd ) {
throw new IllegalArgumentException("Start cannot exceed End.");
}
//get the range, casting to long to avoid overflow problems
long range = (long)aEnd - (long)aStart + 1;
// compute a fraction of the range, 0 <= frac < range
long fraction = (long)(range * aRandom.nextDouble());
int randomNumber = (int)(fraction + aStart);
log("Generated : " + randomNumber);
}
private static void log(String aMessage){
System.out.println(aMessage);
}
}
Um exemplo desta classe :
Generating random integers in the range 1..10.
Generated : 9
Generated : 3
Generated : 3
Generated : 9
Generated : 4
Generated : 1
Generated : 3
Generated : 9
Generated : 10
Generated : 10
Done.
Você pode conseguir isso de forma concisa em Java 8:
Random random = new Random();
int max = 10;
int min = 5;
int totalNumber = 10;
IntStream stream = random.ints(totalNumber, min, max);
stream.forEach(System.out::println);
Aqui está uma amostra simples que mostra como gerar um número aleatório a partir do intervalo fechado [min, max]
, enquanto min <= max is true
Você pode reutilizá-lo como campo na classe hole, também tendo todos os métodos Random.class
num só lugar
Exemplo de resultados:
RandomUtils random = new RandomUtils();
random.nextInt(0, 0); // returns 0
random.nextInt(10, 10); // returns 10
random.nextInt(-10, 10); // returns numbers from -10 to 10 (-10, -9....9, 10)
random.nextInt(10, -10); // throws assert
Fontes:
import junit.framework.Assert;
import java.util.Random;
public class RandomUtils extends Random {
/**
* @param min generated value. Can't be > then max
* @param max generated value
* @return values in closed range [min, max].
*/
public int nextInt(int min, int max) {
Assert.assertFalse("min can't be > then max; values:[" + min + ", " + max + "]", min > max);
if (min == max) {
return max;
}
return nextInt(max - min + 1) + min;
}
}
Basta usar a Aleatória classe:
Random ran = new Random();
// Assumes max and min are non-negative.
int randomInt = min + ran.nextInt(max - min + 1);
Outra opção é apenas usar Apache Commons:
import org.apache.commons.math.random.RandomData;
import org.apache.commons.math.random.RandomDataImpl;
public void method() {
RandomData randomData = new RandomDataImpl();
int number = randomData.nextInt(5, 10);
// ...
}
Se quiser tentar a resposta com o maior número de votos acima, pode simplesmente usar este código:
public class Randomizer
{
public static int generate(int min,int max)
{
return min + (int)(Math.random() * ((max - min) + 1));
}
public static void main(String[] args)
{
System.out.println(Randomizer.generate(0,10));
}
}
É simples e limpo.
private static Random random = new Random();
public static int getRandomInt(int min, int max){
return random.nextInt(max - min + 1) + min;
}
Ou
public static int getRandomInt(Random random, int min, int max)
{
return random.nextInt(max - min + 1) + min;
}
É melhor usar SecureRandom do que apenas Aleatório.
public static int generateRandomInteger(int min, int max) {
SecureRandom rand = new SecureRandom();
rand.setSeed(new Date().getTime());
int randomNum = rand.nextInt((max - min) + 1) + min;
return randomNum;
}
rand.nextInt((max+1) - min) + min;
Isto está a funcionar bem.