Как мне сгенерировать случайные целые числа в определенном диапазоне в Java?

avatar
user42155
12 декабря 2008 в 18:20
4469543
72
3778

Как мне сгенерировать случайное значение int в определенном диапазоне?

Я пробовал следующее, но они не работают:

Попытка 1:

randomNum = minimum + (int)(Math.random() * maximum);

Ошибка: randomNum может быть больше, чем maximum.

Попытка 2:

Random rn = new Random();
int n = maximum - minimum + 1;
int i = rn.nextInt() % n;
randomNum =  minimum + i;

Ошибка: randomNum может быть меньше, чем minimum.

Источник
raupach
13 декабря 2008 в 10:18
0

Когда вам нужно много случайных чисел, я не рекомендую использовать класс Random в API. Просто у него слишком маленький период. Попробуйте вместо этого твистер Мерсенна. Существует реализация Java.

janniks
3 февраля 2020 в 11:53
20

Прежде чем опубликовать новый ответ, подумайте, что на этот вопрос уже есть более 65 ответов. Пожалуйста, убедитесь, что ваш ответ содержит информацию, которой нет среди существующих ответов.

NomadMaker
18 февраля 2021 в 17:20
0

randomNum = minimum + (int)(Math.random() * (maximum - minimum);

Ответы (72)

avatar
M. Justin
30 декабря 2021 в 08:30
0

Java 17 представила интерфейс RandomGenerator, который предоставляет метод int nextInt(int origin, int bound) для получения случайного целого числа в диапазоне: <395460645110

// Returns a random int between minimum (inclusive) & maximum (exclusive)
int randomInt = RandomGenerator.getDefault().nextInt(minimum, maximum);

В дополнение к использованию для ряда новых алгоритмов случайной генерации, этот интерфейс был добавлен к существующим классам случайной генерации (Random, SecureRandom, <395460645 > SplittableRandom и ThreadLocalRandom). Это означает, что начиная с Java 17 все эти классы имеют этот ограниченный метод nextInt:

new Random().nextInt(minimum, maximum);
new SecureRandom().nextInt(minimum, maximum);
new SplittableRandom().nextInt(minimum, maximum);
new ThreadLocalRandom().nextInt(minimum, maximum);

avatar
Harun ÇETİN
24 декабря 2021 в 03:27
-1

Если у нас есть чувствительные к безопасности приложения, мы должны использовать SecureRandom.

    import java.security.SecureRandom;

    public class Main {
      public static void main(String... args){
        int max=13;
        int min =1;
        int randomWithSecureRandom = new SecureRandom().nextInt(max - min) + min;
        System.out.println(randomWithSecureRandom);
      }
    }
avatar
Musfiq Shanta
24 августа 2021 в 03:28
3

int randomNum = 5+ (int) (Math.random () * 5);

Диапазон 5-10

avatar
Shital Ghimire
28 июня 2021 в 12:25
1
Random rng = new Random();
int min = 3;
int max = 11;
int upperBound = max - min + 1; // upper bound is exclusive, so +1
int num = min + rng.nextInt(upperBound);
System.out.println(num);
avatar
dreamcrash
27 января 2021 в 18:09
1

Чтобы избежать повторения того, что было сказано несколько раз, я показываю альтернативу для тех, кому нужен криптографически более сильный генератор псевдослучайных чисел, используя класс SecureRandom, который расширяет класс Random. Из источника можно прочитать:

Этот класс предоставляет криптографически стойкий генератор случайных чисел (ГСЧ). Криптографически стойкое случайное число минимально соответствует с тестами статистического генератора случайных чисел, указанными в FIPS 140-2, Требования безопасности для криптографических модулей, раздел 4.9.1. Кроме того, SecureRandom должен выдавать недетерминированный вывод. Следовательно, любой исходный материал, переданный объекту SecureRandom, должен быть непредсказуемо, и все выходные последовательности SecureRandom должны быть криптографически стойкий, как описано в RFC 1750: Randomness Рекомендации по безопасности.

Вызывающий получает экземпляр SecureRandom через без аргументов конструктор или один из методов getInstance:

  SecureRandom random = new SecureRandom();  

Многие реализации SecureRandom имеют форму генератора псевдослучайных чисел. (PRNG), что означает, что они используют детерминированный алгоритм для получения псевдослучайная последовательность из истинного случайного начального числа. Другие реализации могут выдавать истинные случайные числа, а другие могут использовать комбинацию обоих методов.

Для генерации случайного числа между значениями min и max включительно:

public static int generate(SecureRandom secureRandom, int min, int max) {
        return min + secureRandom.nextInt((max - min) + 1);
}

для заданных значений min (включительно) и max (исключая):

return min + secureRandom.nextInt((max - min));

Пример рабочего кода:

public class Main {

    public static int generate(SecureRandom secureRandom, int min, int max) {
        return min + secureRandom.nextInt((max - min) + 1);
    }

    public static void main(String[] arg) {
        SecureRandom random = new SecureRandom();
        System.out.println(generate(random, 0, 2 ));
    }
}

Источник, например coderhelper, baeldung, geeksforgeeks, обеспечивает сравнение между <208034520985034> классами <2080345209850345> и.

Из baeldung можно прочитать:

Наиболее распространенный способ использования SecureRandom - это генерация int, long, значения типа float, double или логические:

int randomInt = secureRandom.nextInt ();
длинный randomLong = secureRandom.nextLong ();
float randomFloat = secureRandom.nextFloat ();
двойной randomDouble = secureRandom.nextDouble ();
логическое randomBoolean = secureRandom.nextBoolean ();

Для генерации значений int мы можем передать верхнюю границу в качестве параметра:

int randomInt = secureRandom.nextInt (upperBound);

Кроме того, мы можем сгенерировать поток значений для int, double и long:

IntStream randomIntStream = secureRandom.ints ();
LongStream randomLongStream = secureRandom.longs ();
DoubleStream randomDoubleStream = secureRandom.doubles ();

Для всех потоков мы можем явно установить размер потока:

IntStream intStream = secureRandom.ints (streamSize);

Этот класс предлагает несколько других вариантов (, например, выбор базового генератора случайных чисел), которые выходят за рамки этого вопроса.

avatar
Hasee Amarathunga
8 октября 2020 в 05:18
3

Для этого вы можете использовать следующий способ

int range = 10;
int min = 5
Random r = new Random();
int  = r.nextInt(range) + min;
avatar
Anand
29 мая 2020 в 04:47
3

Используйте Apache Lang3 Commons

Integer.parseInt(RandomStringUtils.randomNumeric(6, 6));

Мин. Значение от 100000 до максимального значения 999999

user2719152
9 июля 2020 в 03:34
0

Зачем усложнять жизнь, когда можно найти простые решения :)

Anand
9 июля 2020 в 11:23
0

Я подумал, что это было проще всего с учетом случайных чисел в диапазоне.

Saikat
28 июля 2020 в 07:32
0

Сгенерированный номер может начинаться с нуля!

Raimund Krämer
22 ноября 2020 в 13:25
0

Это дает строку, а не целое число, и поэтому не является ответом на вопрос.

Anand
24 ноября 2020 в 12:20
0

Возвращает \ p {Digit}

avatar
Lokesh Sharma
4 мая 2020 в 14:48
2
int func(int max, int min){

      int range = max - min + 1;
      
      // Math.random() function will return a random no between [0.0,1.0).
      int res = (int) ( Math.random()*range)+min;

      return res;
}
Pang
12 августа 2020 в 01:03
0

Похоже, это просто повторение многих из существующих ответов.

avatar
Rahul Dhiman
16 декабря 2019 в 10:56
-4

Следующий фрагмент даст случайное значение от 0 до 10000:

import java.util.Random;
public class Main
{
    public static void main(String[] args) {
        Random rand = new Random();
        System.out.printf("%04d%n", rand.nextInt(10000));
    }
}
Toby Speight
16 декабря 2019 в 11:17
10

Спасибо за этот фрагмент кода, который может предоставить некоторую краткосрочную помощь. Правильное объяснение значительно улучшило бы его долгосрочную ценность, показав , почему это хорошее решение проблемы, и сделало бы его более полезным для будущих читателей с другими похожими вопросами. Измените свой ответ, чтобы добавить пояснения, включая сделанные вами предположения. В частности, не очевидно, как этот код принимает нижнюю и верхнюю границы постановки задачи.

avatar
Kaplan
6 июля 2019 в 09:02
0

вот функция, которая возвращает ровно одно целое случайное число в диапазоне, определяемом параметрами lowerBoundIncluded и upperBoundIncluded <94922549640>, запрошено пользователем >

SplittableRandom splittableRandom = new SplittableRandom();

BiFunction<Integer,Integer,Integer> randomInt = (lowerBoundIncluded, upperBoundIncluded)
    -> splittableRandom.nextInt( lowerBoundIncluded, upperBoundIncluded + 1 );

randomInt.apply( …, … ); // gets the random number


… или короче для одноразовой генерации случайного числа

new SplittableRandom().nextInt( lowerBoundIncluded, upperBoundIncluded + 1 );

avatar
Anshul Singhal
13 мая 2019 в 09:04
6

Можно использовать следующий код:

ThreadLocalRandom.current().nextInt(rangeStart, rangeEndExclusive)
Maarten Bodewes
1 июля 2019 в 11:28
2

Было несколько ответов, которые уже предлагали ThreadLocalRandom. Если вопрос был защищен, пожалуйста, будьте особенно осторожны, чтобы не дублировать ответы.

avatar
Anjali Pavithra
1 января 2019 в 09:39
-4

Вы можете сделать, как показано ниже.

import java.util.Random;
public class RandomTestClass {

    public static void main(String[] args) {
        Random r = new Random();
        int max, min;
        Scanner scanner = new Scanner(System.in);
        System.out.println("Enter maximum value : ");
        max = scanner.nextInt();
        System.out.println("Enter minimum value : ");
        min = scanner.nextInt();
        int randomNum;
        randomNum = r.nextInt(max) + min;
        System.out.println("Random Number : " + randomNum);
    }

}
avatar
Prakhar Nigam
17 ноября 2018 в 07:46
3

Используйте java.util for Random для общего использования.

Вы можете определить свой минимальный и максимальный диапазон, чтобы получить эти результаты.

Random rand=new Random();
rand.nextInt((max+1) - min) + min;
avatar
Alekya
22 августа 2018 в 06:46
2
public static void main(String[] args) {

    Random ran = new Random();

    int min, max;
    Scanner sc = new Scanner(System.in);
    System.out.println("Enter min range:");
    min = sc.nextInt();
    System.out.println("Enter max range:");
    max = sc.nextInt();
    int num = ran.nextInt(min);
    int num1 = ran.nextInt(max);
    System.out.println("Random Number between given range is " + num1);

}
avatar
monster
14 августа 2018 в 12:25
4

Внесение следующего изменения в Попытка 1 должна работать -

randomNum = minimum + (int)(Math.random() * (maximum - minimum) );

Проверьте этот на наличие рабочего кода.

avatar
vaquar khan
31 мая 2018 в 15:16
5
import java.util.Random;

public class RandomSSNTest {

    public static void main(String args[]) {
        generateDummySSNNumber();
    }


    //831-33-6049
    public static void generateDummySSNNumber() {
        Random random = new Random();

        int id1 = random.nextInt(1000);//3
        int id2 = random.nextInt(100);//2
        int id3 = random.nextInt(10000);//4

        System.out.print((id1+"-"+id2+"-"+id3));
    }

}

Вы также можете использовать

import java.util.concurrent.ThreadLocalRandom;
Random random = ThreadLocalRandom.current();

Однако этот класс плохо работает в многопоточной среде.

Peter Mortensen
5 января 2019 в 10:18
1

Объяснение было бы в порядке.

avatar
Sanjeev Singh
23 мая 2018 в 15:24
3

Ниже приведен еще один пример использования Random и forEach

int firstNum = 20;//Inclusive
int lastNum = 50;//Exclusive
int streamSize = 10;
Random num = new Random().ints(10, 20, 50).forEach(System.out::println);
avatar
Oleksandr Pyrohov
11 апреля 2018 в 21:54
27

Начиная с Java 7, вы больше не должны использовать Random. Для большинства применений выбор генератора случайных чисел теперь ThreadLocalRandom.

Для групповых объединений и параллельных потоки используйте SplittableRandom.

Джошуа Блох. Эффективная Java. Третье издание.

Начиная с Java 8

Для пулов fork join и параллельных потоков используйте SplittableRandom, который обычно работает быстрее, имеет лучшие свойства статистической независимости и однородности по сравнению с Random.

Для создания случайного int в диапазоне [0, 1_000]:

int n = new SplittableRandom().nextInt(0, 1_001);

Для создания случайного int[100] массива значений в диапазоне [0, 1_000]:

int[] a = new SplittableRandom().ints(100, 0, 1_001).parallel().toArray();

Чтобы вернуть поток случайных значений:

IntStream stream = new SplittableRandom().ints(100, 0, 1_001);
Johnbot
20 июля 2018 в 06:29
0

Есть ли причина, по которой пример включает .parallel()? Мне кажется, что создание 100 случайных чисел было бы слишком тривиально, чтобы гарантировать параллелизм.

Oleksandr Pyrohov
20 июля 2018 в 08:35
0

@Johnbot Спасибо за комментарий, вы правы. Но основная причина заключалась в том, чтобы показать API (конечно, умный путь - измерить производительность перед использованием обработки parallel). Кстати, для массива элементов 1_000_000 версия parallel на моей машине была в 2 раза быстрее по сравнению с последовательной.

avatar
Siddhartha Thota
25 февраля 2018 в 20:26
4

Допустим, вам нужен диапазон от 0 до 9, 0 - минимум, 9 - максимум. Приведенная ниже функция напечатает что-либо от 0 до 9. Она одинакова для всех диапазонов.

public static void main(String[] args) {
    int b = randomNumberRange(0, 9);
    int d = randomNumberRange (100, 200);
    System.out.println("value of b is " + b);
    System.out.println("value of d is " + d);
}

public static int randomNumberRange(int min, int max) {
    int n = (max + 1 - min) + min;
    return (int) (Math.random() * n);
}
user10253771
23 января 2019 в 01:03
0

Это не выглядит правильным. В "int n = (max + 1 - min) + min; return (int) (Math.random () * n);" , n = max + 1, и вы просто создаете int в [0, max] вместо [min, max]. Это должно быть «int n = max + 1 - min; return (int) (Math.random () * n) + min;»

avatar
BMAM
1 февраля 2018 в 04:54
3

Приведенный ниже код генерирует случайное число от 100 000 до 900 000. Этот код будет генерировать шестизначные значения. Я использую этот код для создания шестизначного OTP.

Используйте import java.util.Random, чтобы использовать этот случайный метод.

import java.util.Random;

// Six digits random number generation for OTP
Random rnd = new Random();
long longregisterOTP = 100000 + rnd.nextInt(900000);
System.out.println(longregisterOTP);
avatar
ledlogic
1 декабря 2017 в 23:01
2

Существует библиотека по адресу https://sourceforge.net/projects/stochunit/ для обработки выбора диапазонов.

StochIntegerSelector randomIntegerSelector = new StochIntegerSelector();
randomIntegerSelector.setMin(-1);
randomIntegerSelector.setMax(1);
Integer selectInteger = randomIntegerSelector.selectInteger();

Имеет краевое включение / преклюзию.

avatar
Lawakush Kurmi
2 ноября 2017 в 06:38
21

Чтобы сгенерировать случайное число «между двумя числами», используйте следующий код:

Random r = new Random();
int lowerBound = 1;
int upperBound = 11;
int result = r.nextInt(upperBound-lowerBound) + lowerBound;

Это дает вам случайное число от 1 (включительно) до 11 (исключая), поэтому инициализируйте значение upperBound, добавив 1. Например, если вы хотите сгенерировать случайное число от 1 до 10, инициализируйте число upperBound с помощью 11 вместо 10.

avatar
namezhouyu
9 октября 2017 в 08:48
6
Random random = new Random();
int max = 10;
int min = 3;
int randomNum = random.nextInt(max) % (max - min + 1) + min;
Peter Mortensen
5 января 2019 в 10:21
0

Объяснение было бы в порядке.

avatar
Sam2016
4 октября 2017 в 14:18
0

Простой способ сгенерировать n случайных чисел от a до b например, a = 90, b = 100, n = 20

Random r = new Random();
for(int i =0; i<20; i++){
    System.out.println(r.ints(90, 100).iterator().nextInt());
}

r.ints() возвращает IntStream и имеет несколько полезных методов, посмотрите его API.

Maarten Bodewes
5 мая 2020 в 19:51
0

Помимо того, что есть другие ответы, в которых используются потоки, по крайней мере, они не создают новый поток в цикле, теперь это действительно не имеет смысла.

avatar
Gihan Chathuranga
12 августа 2017 в 14:10
4

Это самый простой способ сделать это.

import java.util.Random;
class Example{
    public static void main(String args[]){
        /*-To test-
        for(int i = 1 ;i<20 ; i++){
            System.out.print(randomnumber()+",");
        }
        */

        int randomnumber = randomnumber();

    }

    public static int randomnumber(){
        Random rand = new Random();
        int randomNum = rand.nextInt(6) + 5;

        return randomNum;
    }
}

Здесь 5 - начальная точка случайных чисел. 6 - это диапазон, включающий число 5.

avatar
user5150135
20 июня 2017 в 12:39
18

Этого можно добиться в 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);
avatar
Simon
28 мая 2017 в 14:30
34

Я использую это:

 /**
   * @param min - The minimum.
   * @param max - The maximum.
   * @return A random double between these numbers (inclusive the minimum and maximum).
   */
 public static double getRandom(double min, double max) {
   return (Math.random() * (max + 1 - min)) + min;
 }

Вы можете преобразовать его в целое число, если хотите.

sokras
20 июля 2017 в 07:38
0

Эта функция выдает одно и то же число снова и снова. В моем случае это было: 2147483647

Maarten Bodewes
23 апреля 2018 в 21:26
0

Неудача: у вас есть функция, которая требует двойного, а затем выполнения +1? Это определенно противоречит принципу наименьшего удивления. Что произойдет, если вы используете min = 0,1 и max = 0,2?

Maarten Bodewes
23 апреля 2018 в 21:36
0

@sokras метод вызывает new Random (проверьте JavaDoc): «Создает новый генератор случайных чисел. Этот конструктор устанавливает для начального числа генератора случайных чисел значение, которое, скорее всего, будет отличаться от любого другого вызова этого конструктора». Скорее всего, можно просто использовать текущее время в качестве начального числа. Если в это время используются миллисекунды, то современные компьютеры достаточно быстры, чтобы сгенерировать то же число. Но помимо этого 2147483647 - это Integer.MAX_VALUE; вывод, очевидно, зависит от ввода, который вы не указали.

avatar
Divyesh Kanzariya
26 мая 2017 в 13:24
4

Если вы уже используете Commons Lang API 2.x или последнюю версию, тогда существует один класс для генерации случайных чисел RandomUtils.

public static int nextInt(int n)

Возвращает псевдослучайное, равномерно распределенное значение int от 0 (включительно) до указанного значения (исключая) из последовательности Math.random ().

Параметры: n - указанное исключительное максимальное значение

int random = RandomUtils.nextInt(1000000);

Примечание: в RandomUtils есть много методов для генерации случайных чисел

avatar
Jake O
26 апреля 2017 в 12:30
0

Использование потоков Java 8,

  • Передайте initialCapacity - Сколько чисел
  • Передайте randomBound - от x до randomBound
  • Передавать true / false для сортировки или нет
  • Передать новый объект Random ()

public static List<Integer> generateNumbers(int initialCapacity, int randomBound, Boolean sorted, Random random) {

    List<Integer> numbers = random.ints(initialCapacity, 1, randomBound).boxed().collect(Collectors.toList());

    if (sorted)
        numbers.sort(null);

    return numbers;
}

Он генерирует числа из 1-Randombound в этом примере.

avatar
AndroidGeek
19 января 2017 в 06:37
3

Я создал метод для получения уникального целого числа в заданном диапазоне.

/*
      * minNum is the minimum possible random number
      * maxNum is the maximum possible random number
      * numbersNeeded is the quantity of random number required
      * the give method provides you with unique random number between min & max range
*/
public static Set<Integer> getUniqueRandomNumbers( int minNum , int maxNum ,int numbersNeeded ){

    if(minNum >= maxNum)
        throw new IllegalArgumentException("maxNum must be greater than minNum");

    if(! (numbersNeeded > (maxNum - minNum + 1) ))
        throw new IllegalArgumentException("numberNeeded must be greater then difference b/w (max- min +1)");

    Random rng = new Random(); // Ideally just create one instance globally

    // Note: use LinkedHashSet to maintain insertion order
    Set<Integer> generated = new LinkedHashSet<Integer>();
    while (generated.size() < numbersNeeded)
    {
        Integer next = rng.nextInt((maxNum - minNum) + 1) + minNum;

        // As we're adding to a set, this will automatically do a containment check
        generated.add(next);
    }
    return generated;
}
avatar
firephil
21 декабря 2016 в 23:37
6

Другой подход с использованием Java 8 IntStream и Collections.shuffle

import java.util.stream.IntStream;
import java.util.ArrayList;
import java.util.Collections;

public class Main {

    public static void main(String[] args) {

        IntStream range = IntStream.rangeClosed(5,10);
        ArrayList<Integer> ls =  new ArrayList<Integer>();

        //populate the ArrayList
        range.forEach(i -> ls.add(new Integer(i)) );

        //perform a random shuffle  using the Collections Fisher-Yates shuffle
        Collections.shuffle(ls);
        System.out.println(ls);
    }
}

Эквивалент в Scala

import scala.util.Random

object RandomRange extends App{
  val x =  Random.shuffle(5 to 10)
    println(x)
}
Eric Duminil
27 февраля 2017 в 20:27
0

Хороший. Вы можете использовать List<Integer> ls = range.boxed().collect(Collectors.toList());

Eric Duminil
27 февраля 2017 в 20:28
0

new Integer (i) также был избыточным, но он все равно удаляется кодом из моего предыдущего комментария.

charles-allen
2 августа 2017 в 13:44
1

Разве это не дает 6 чисел в случайном порядке, а не одно число? Кажется немного расточительным. И если мне нужно еще одно случайное число, я не могу просто взять второе в списке, потому что у него нет шансов быть таким же, как уже взятое число.

avatar
false9striker
2 декабря 2016 в 18:16
5

Вы можете использовать

RandomStringUtils.randomNumeric(int count)

метод также из общего доступа Apache.

avatar
user_3380739
28 ноября 2016 в 22:33
2

Большинство приведенных выше предложений не рассматривают «переполнение», например: min = Integer.MIN_VALUE, max = 100. Один из правильных подходов, которые у меня есть до сих пор:

final long mod = max- min + 1L;
final int next = (int) (Math.abs(rand.nextLong() % mod) + min);
Maarten Bodewes
19 июня 2017 в 21:29
0

Создание операторов защиты (если значение> другое значение, тогда исключение) также должно работать (при условии, что диапазон не установлен пользователем / системой).

avatar
Hiren Patel
26 сентября 2016 в 20:13
3

Будет сгенерирован список случайных чисел с диапазоном (мин - макс) с без дубликатов .

generateRandomListNoDuplicate(1000, 8000, 500);

Добавьте этот метод.

private void generateRandomListNoDuplicate(int min, int max, int totalNoRequired) {
    Random rng = new Random();
    Set<Integer> generatedList = new LinkedHashSet<>();
    while (generatedList.size() < totalNoRequired) {
        Integer radnomInt = rng.nextInt(max - min + 1) + min;
        generatedList.add(radnomInt);
    }
}

Надеюсь, это вам поможет.

Maarten Bodewes
1 марта 2017 в 21:39
0

Это становится сложным, если вы нашли большинство чисел в пределах диапазона; есть более эффективные способы сделать это (например, генерировать случайное число с максимальным значением, равным количеству оставшихся элементов, и пропускать уже найденные числа. На самом деле, как в Бинго.

avatar
Andrew
29 октября 2015 в 20:46
2

Случайное число из диапазона [min..max] включительно:

int randomFromMinToMaxInclusive = ThreadLocalRandom.current()
        .nextInt(min, max + 1);
avatar
gifpif
27 мая 2015 в 10:43
27

Сгенерируйте случайное число для разницы минимального и максимального значений с помощью метода nextint (n), а затем добавьте минимальное число к результату:

Random rn = new Random();
int result = rn.nextInt(max - min + 1) + min;
System.out.println(result);
avatar
thangaraj
8 апреля 2015 в 14:14
5

Вы можете сделать что-то вроде этого:

import java.awt.*;
import java.io.*;
import java.util.*;
import java.math.*;

public class Test {

    public static void main(String[] args) {
        int first, second;

        Scanner myScanner = new Scanner(System.in);

        System.out.println("Enter first integer: ");
        int numOne;
        numOne = myScanner.nextInt();
        System.out.println("You have keyed in " + numOne);

        System.out.println("Enter second integer: ");
        int numTwo;
        numTwo = myScanner.nextInt();
        System.out.println("You have keyed in " + numTwo);

        Random generator = new Random();
        int num = (int)(Math.random()*numTwo);
        System.out.println("Random number: " + ((num>numOne)?num:numOne+num));
    }
}
avatar
grep
26 марта 2015 в 13:02
14

Лучше использовать SecureRandom, чем просто Random.

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;
}
maraca
16 апреля 2015 в 19:30
1

Это не так хорошо, потому что, если он выполняется за одну и ту же миллисекунду, вы получите то же число, вам нужно поместить инициализацию rand и setSeet вне метода.

grep
17 апреля 2015 в 12:03
0

Да, вам нужен seed, но с использованием SecureRandom.

maraca
18 апреля 2015 в 09:19
0

Извините, но тот, кто отклонил запрос на изменение, понятия не имеет о программировании на Java Это хорошее предложение, но как таковое оно неверно , потому что, если оно выполняется за ту же миллисекунду, оно даст то же самое. число, а не случайное.

maraca
18 апреля 2015 в 09:30
0

Правильного решения нигде не найти, не многие люди знают блоки статического инициализатора ... это то, что вы должны использовать для установки семени: 1: private static int SecureRandom rand = new SecureRandom(); 2: static { 3: rand.setSeed(...); 4: }

Maarten Bodewes
1 марта 2017 в 21:32
6

Нет никакой необходимости в посеве SecureRandom, он будет посеян системой. Прямой вызов setSeed очень опасен, он может заменить (действительно случайное) начальное число датой. И это, безусловно, , а не приведет к SecureRandom, так как любой может угадать время и попытаться заполнить свой собственный экземпляр SecureRandom этой информацией.

avatar
hexabunny
12 марта 2015 в 22:44
105

Достаточно небольшой модификации вашего первого решения.

Random rand = new Random();
randomNum = minimum + rand.nextInt((maximum - minimum) + 1);

Подробнее о реализации Random

см. Здесь
AxelH
8 июля 2016 в 12:30
0

Для минимума <= значение <максимум я сделал то же самое с Math: randomNum = minimum + (int) (Math.random () * (maximum-minimum)); но приведение не очень хорошее увидеть ;)

Maarten Bodewes
5 мая 2020 в 19:55
0

Повторный ответ с опозданием минимум на 7 лет.

frankfurt-laravel
9 марта 2021 в 12:58
0

Для меня как новичка это было наиболее легко реализовать. Спасибо!

avatar
Muhammad Aamir Talib
11 февраля 2015 в 11:40
11
private static Random random = new Random();    

public static int getRandomInt(int min, int max){
  return random.nextInt(max - min + 1) + min;
}

ИЛИ

public static int getRandomInt(Random random, int min, int max)
{
  return random.nextInt(max - min + 1) + min;
}
Warren MacEvoy
17 августа 2016 в 21:46
0

Если max и min большие, это вызовет проблемы с переполнением и даст неверные результаты.

avatar
Yakiv Mospan
28 ноября 2014 в 00:50
13

Вот простой пример, который показывает, как сгенерировать случайное число из закрытого диапазона [min, max], а min <= max is true

Вы можете повторно использовать его как поле в классе отверстий, также имея все методы Random.class в одном месте

Пример результатов:

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

Источники :

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;
    }
}
avatar
Alexis C.
26 ноября 2014 в 18:29
171

В java-8 они представили метод ints(int randomNumberOrigin, int randomNumberBound) в классе Random <20640874> .1548> .1548

Например, если вы хотите сгенерировать пять случайных целых чисел (или одно) в диапазоне [0, 10], просто выполните:

Random r = new Random();
int[] fiveRandomNumbers = r.ints(5, 0, 11).toArray();
int randomNumber = r.ints(1, 0, 11).findFirst().getAsInt();

Первый параметр указывает только размер сгенерированного IntStream (который является перегруженным методом метода, который создает неограниченное IntStream).

Если вам нужно выполнить несколько отдельных вызовов, вы можете создать бесконечный примитивный итератор из потока:

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();
    }
}

Вы также можете сделать это для значений double и long. Я надеюсь, что это помогает! :)

Naxos84
26 февраля 2018 в 07:13
3

Я бы посоветовал вам создать экземпляр randomIterator только один раз. См. Комментарий Грега Кейса к его собственному ответу.

avatar
Sunil Chawla
3 августа 2014 в 03:07
31

Давайте рассмотрим пример.

Предположим, я хочу сгенерировать число от 5-10 :

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);

Давайте разберемся с этим ...

Инициализируйте max с наибольшим значением и min с наименьшим значением.

Теперь нам нужно определить, сколько возможных значений можно получить. В этом примере это будет:

5, 6, 7, 8, 9, 10

Таким образом, это будет максимум - минимум +1.

т.е. 10-5 + 1 = 6

Случайное число будет генерировать число от 0-5 .

т.е. 0, 1, 2, 3, 4, 5

Добавление значения min к случайному числу даст:

5, 6, 7, 8, 9, 10

Следовательно, мы получаем желаемый диапазон.

avatar
yottabrain
14 июня 2014 в 03:50
6
import java.util.Random; 

public class RandomUtil {
    // Declare as class variable so that it is not re-seeded every call
    private static Random random = new Random();

    /**
     * Returns a psuedo-random number between min and max (both inclusive)
     * @param min Minimim value
     * @param max Maximim value. Must be greater than min.
     * @return Integer between min and max (both inclusive)
     * @see java.util.Random#nextInt(int)
     */
    public static int nextInt(int min, int max) {
        // nextInt is normally exclusive of the top value,
        // so add 1 to make it inclusive
        return random.nextInt((max - min) + 1) + min;
    }
}
avatar
f3d0r
24 мая 2014 в 23:21
2

Вы можете использовать класс Random для генерации случайного числа, а затем использовать .nextInt (maxNumber) для генерации случайного числа. MaxNumber - это число, которое вы хотите получить максимум при генерации случайного числа. Однако помните, что класс Random дает вам числа от 0 до maxNumber-1.

Random r = new Random();
int i = r.nextInt();

Другой способ сделать это - использовать класс Math.Random (), который многие классы в школах требуют от вас, потому что он более эффективен и вам не нужно объявлять новый объект Random. Чтобы получить случайное число с помощью Math.Random (), введите:

Math.random() * (max - min) + min;
avatar
Jorge
15 января 2014 в 00:51
6

Я просто укажу, что не так с решениями, предоставленными в вопросе, и почему эти ошибки.

Решение 1:

randomNum = minimum + (int)(Math.random()*maximum); 

Проблема: randomNum присвоены значения, превышающие максимальное значение.

Объяснение: Предположим, что наш минимум равен 5, а ваш максимум равен 10. Любое значение из Math.random() больше 0,6 приведет к оценке выражения до 6 или больше, а добавление 5 сделает его больше 10 (ваш максимум). Проблема в том, что вы умножаете случайное число на максимум (что дает число, почти равное максимальному), а затем добавляете минимум. Если минимальное значение не равно 1, это неверно. Вы должны переключиться на, как упоминалось в других ответах,

randomNum = minimum + (int)(Math.random()*(maximum-minimum+1))

+1 потому, что Math.random() никогда не вернет 1.0.

Решение 2:

Random rn = new Random();
int n = maximum - minimum + 1;
int i = rn.nextInt() % n;
randomNum =  minimum + i;

Ваша проблема в том, что «%» может возвращать отрицательное число, если первый член меньше 0. Поскольку rn.nextInt() возвращает отрицательные значения с вероятностью ~ 50%, вы также не получите ожидаемого результата.

Это было, однако, почти идеально. Вам просто нужно было посмотреть немного дальше в Javadoc, nextInt (int n). При наличии этого метода выполнение

Random rn = new Random();
int n = maximum - minimum + 1;
int i = rn.nextInt(n);
randomNum =  minimum + i;

Также вернет желаемый результат.

Jaroslaw Pawlak
9 марта 2015 в 15:52
1

% имеет еще большую проблему смещения распределения. Недавно я написал об этом в блоге: jaroslawpawlak.wordpress.com/2014/10/11/…

avatar
Prof Mo
24 декабря 2013 в 13:33
22

Просто используйте Random класс:

Random ran = new Random();
// Assumes max and min are non-negative.
int randomInt = min + ran.nextInt(max - min + 1);
Maarten Bodewes
19 июня 2017 в 21:21
9

Я не вижу здесь ничего нового, что не было опубликовано в бесчисленных предыдущих постах.

parsecer
26 марта 2021 в 20:22
0

@MaartenBodewes Эти бесчисленные сообщения трудно найти. Некоторые другие методы наверху

Maarten Bodewes
26 марта 2021 в 20:31
0

Да, публикация очередного обмана не поможет против этого. Проголосуйте за другие ответы или добавьте детали. В противном случае это просто фарм репутации.

avatar
user591593
24 ноября 2013 в 14:15
5

Я собираюсь линейно нормализовать сгенерированные случайные числа в желаемый диапазон, используя следующее. Пусть x будет случайным числом, пусть a и b будут минимальным и максимальным диапазоном желаемого нормализованного числа.

Затем ниже приведен очень простой фрагмент кода для проверки диапазона, полученного линейным отображением.

public static void main(String[] args) {
    int a = 100;
    int b = 1000;
    int lowest = b;
    int highest = a;
    int count = 100000;
    Random random = new Random();
    for (int i = 0; i < count; i++) {
        int nextNumber = (int) ((Math.abs(random.nextDouble()) * (b - a))) + a;
        if (nextNumber < a || nextNumber > b) {
            System.err.println("number not in range :" + nextNumber);
        }
        else {
            System.out.println(nextNumber);
        }
        if (nextNumber < lowest) {
            lowest = nextNumber;
        }
        if (nextNumber > highest) {
            highest = nextNumber;
        }
    }
    System.out.println("Produced " + count + " numbers from " + lowest
            + " to " + highest);
}
avatar
Akash Malhotra
23 сентября 2013 в 09:24
3

Я думаю, что этот код подойдет для этого. Попробуйте это:

import java.util.Random;
public final class RandomNumber {

    public static final void main(String... aArgs) {
        log("Generating 10 random integers in range 1..10.");
        int START = 1;
        int END = 10;
        Random randomGenerator = new Random();
        for (int idx=1; idx<=10; ++idx) {

            // int randomInt=randomGenerator.nextInt(100);
            // log("Generated : " + randomInt);
            showRandomInteger(START,END,randomGenerator);
        }
        log("Done");
    }

    private static void log(String aMessage) {
        System.out.println(aMessage);
    }

    private static void showRandomInteger(int aStart, int aEnd, Random aRandom) {
        if (aStart > aEnd) {
            throw new IllegalArgumentException("Start cannot exceed End.");
        }
        long range = (long)aEnd - (long)aStart + 1;
        long fraction = (long) (range * aRandom.nextDouble());
        int randomNumber = (int) (fraction + aStart);
        log("Generated" + randomNumber);
    }
}
avatar
Abel Callejo
1 сентября 2013 в 02:53
54

Это можно сделать, просто выполнив инструкцию:

Randomizer.generate(0,10); //min of zero, max of ten

Ниже его исходный код

Randomizer.java

public class Randomizer {
    public static int generate(int min,int max) {
        return min + (int)(Math.random() * ((max - min) + 1));
    }
}

Это просто и понятно.

Maarten Bodewes
19 июня 2017 в 21:23
5

Это могло быть правка другого примера, теперь это просто явная копия для репутации. Указание на «ответ с наибольшим количеством голосов» тоже не очень прямое дело, оно может измениться.

Abel Callejo
20 июня 2017 в 00:36
1

Правильно @MaartenBodewes. Когда я писал этот ответ, ответ, набравший наибольшее количество голосов выше, все еще был написан как решение, подобное алгоритму. Вышеупомянутое решение сильно изменилось, и теперь этот ответ выглядел как подражатель.

Leevi L
8 октября 2019 в 08:31
0

Я действительно не понимаю, почему такие фундаментальные фрагменты кода не являются частью стандартных библиотек Java. Почему я должен это реализовать?

avatar
agpt
7 июня 2013 в 15:14
2

Попробуйте использовать класс org.apache.commons.lang.RandomStringUtils. Да, иногда он дает повторяющееся число рядом, но дает значение от 5 до 15:

    while (true)
    {
        int abc = Integer.valueOf(RandomStringUtils.randomNumeric(1));
        int cd = Integer.valueOf(RandomStringUtils.randomNumeric(2));
        if ((cd-abc) >= 5 && (cd-abc) <= 15)
        {
            System.out.println(cd-abc);
            break;
        }
    }
avatar
andrew
12 февраля 2013 в 23:19
90

ThreadLocalRandom эквивалент класса java.util.Random для многопоточной среды. Генерация случайного числа выполняется локально в каждом из потоков. Таким образом, у нас есть лучшая производительность за счет уменьшения конфликтов.

int rand = ThreadLocalRandom.current().nextInt(x,y);

x, y - интервалы, например (1,10)

avatar
Arun Abraham
5 декабря 2012 в 17:28
3

Один из моих друзей задал мне сегодня тот же вопрос в университете (его требования заключались в том, чтобы сгенерировать случайное число от 1 до -1). Итак, я написал это, и до сих пор он отлично работает с моим тестированием. В идеале существует множество способов генерировать случайные числа из заданного диапазона. Попробуйте это:

Функция:

private static float getRandomNumberBetween(float numberOne, float numberTwo) throws Exception{

    if (numberOne == numberTwo){
        throw new Exception("Both the numbers can not be equal");
    }

    float rand = (float) Math.random();
    float highRange = Math.max(numberOne, numberTwo);
    float lowRange = Math.min(numberOne, numberTwo);

    float lowRand = (float) Math.floor(rand-1);
    float highRand = (float) Math.ceil(rand+1);

    float genRand = (highRange-lowRange)*((rand-lowRand)/(highRand-lowRand))+lowRange;

    return genRand;
}

Выполнить так:

System.out.println( getRandomNumberBetween(1,-1));
Warren MacEvoy
17 августа 2016 в 22:25
0

Попробуйте использовать другие диапазоны, ваш код не дает единообразных значений в данном диапазоне. numberOne = 3.5 и numberTwo = 7.2 дает значения только в диапазоне 4,73–5,96.

avatar
jatin3893
27 октября 2012 в 08:17
4

Я просто генерирую случайное число с помощью Math.random () и умножаю его на большое число, скажем, 10000. Итак, я получаю число от 0 до 10 000 и называю это число i. Теперь, если мне нужны числа между (x, y), сделайте следующее:

i = x + (i % (y - x));

Итак, все i являются числами между x и y.

Чтобы устранить смещение, указанное в комментариях, вместо того, чтобы умножать его на 10000 (или большое число), умножьте его на (y-x).

avatar
sachit
27 октября 2012 в 08:07
6

Вы можете использовать этот фрагмент кода, который решит вашу проблему:

Random r = new Random();
int myRandomNumber = 0;
myRandomNumber = r.nextInt(maxValue-minValue+1)+minValue;

Используйте myRandomNumber (который даст вам число в диапазоне).

avatar
Luke Taylor
12 августа 2012 в 15:01
20

Эти методы могут быть удобными для использования:

Этот метод вернет случайное число между указанным минимальным и максимальным значением:

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;
    }
}

, и этот метод вернет случайное число из предоставленных минимального и максимального значения (так что сгенерированное число также может быть минимальным или максимальным числом):

public static int getRandomNumberFrom(int min, int max) {
    Random foo = new Random();
    int randomNumber = foo.nextInt((max + 1) - min) + min;

    return randomNumber;
}
Maarten Bodewes
1 марта 2017 в 21:26
0

// Since the random number is between the min and max values, simply add 1. Почему? Минут не в счет? Обычно диапазон составляет [min, max), где min включено, а max исключено. Неверный ответ, проголосовали против.

Luke Taylor
2 марта 2017 в 09:53
0

@MaartenBodewes +1 добавлен, потому что getRandomNumberBetween генерирует случайное число, исключая предоставленные конечные точки.

Lii
17 июня 2018 в 12:21
1

Число min + 1 в два раза чаще, чем другое число, будет результатом getRandomNumberBetween!

avatar
Hospes
7 июня 2012 в 10:38
16

Я нашел этот пример Генерация случайных чисел:


В этом примере генерируются случайные целые числа в определенном диапазоне.

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);
  }
} 

Пример выполнения этого класса:

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.
avatar
Garrett Hall
15 февраля 2012 в 16:19
18

Вот полезный класс для генерации случайного ints в диапазоне с любой комбинацией включающих / исключающих границ:

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;
    }
}
avatar
gerardw
18 января 2012 в 16:15
17

Другой вариант - просто использовать 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);
    // ...
 }
avatar
AZ_
13 июля 2011 в 11:31
17
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);
}
avatar
Joel Sjöstrand
10 января 2011 в 13:19
50

Простите за разборчивость, но решение, предложенное большинством, то есть min + rng.nextInt(max - min + 1)), кажется опасным из-за того, что:

  • rng.nextInt(n) не может связаться с Integer.MAX_VALUE.
  • (max - min) ​​может вызвать переполнение, если min отрицательно.

Надежное решение вернет правильные результаты для любого min <= max в пределах [Integer.MIN_VALUE, Integer.MAX_VALUE]. Рассмотрим следующую наивную реализацию:

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;
}

Хотя это неэффективно, обратите внимание, что вероятность успеха в цикле while всегда будет 50% или выше.

M.P. Korstanje
9 января 2015 в 10:27
0

Почему бы не создать исключение IllegalArgumentException, если разница = Integer.MAX_VALUE? Тогда вам не нужен цикл while.

Christian Semrau
6 мая 2015 в 19:27
3

@mpkorstanje Эта реализация предназначена для работы с любыми значениями min <= max, даже если их разница равна или даже больше MAX_VALUE. Запуск цикла до успеха является в этом случае обычным шаблоном, чтобы гарантировать равномерное распределение (если основной источник случайности является однородным). Random.nextInt (int) делает это внутренне, если аргумент не является степенью двойки.

avatar
ganesh
22 февраля 2010 в 11:44
14
rand.nextInt((max+1) - min) + min;

Это нормально работает.

avatar
sam
16 февраля 2010 в 08:50
19

В случае броска кубика это будет случайное число от 1 до 6 (не от 0 до 6), поэтому:

face = 1 + randomNumbers.nextInt(6);
avatar
jackson
4 сентября 2009 в 04:23
409

Использование:

Random ran = new Random();
int x = ran.nextInt(6) + 5;

Целое число x теперь является случайным числом с возможным результатом 5-10.

avatar
Matt R
8 января 2009 в 15:04
74

Класс Math.Random в Java основан на 0. Итак, если вы напишете что-то вроде этого:

Random rand = new Random();
int x = rand.nextInt(10);

x будет между 0-9 включительно.

Итак, учитывая следующий массив элементов 25, код для генерации случайного числа между 0 (основание массива) и array.length будет:

String[] i = new String[25];
Random rand = new Random();
int index = 0;

index = rand.nextInt( i.length );

Поскольку i.length вернет 25, nextInt( i.length ) вернет число в диапазоне 0-24. Другой вариант - Math.Random, который работает таким же образом.

index = (int) Math.floor(Math.random() * i.length);

Для лучшего понимания ознакомьтесь с сообщением на форуме Случайные интервалы (archive.org) .

Tapper7
30 октября 2016 в 05:44
0

+1 для ссылки на скриншот архива wayBackMachine, и ваш ответ по-прежнему полезен для получения "случайных" целых чисел в диапазоне.

charles-allen
2 августа 2017 в 13:53
0

Меня сбивает с толку, почему вы инстанцируете index равным 0.

Matt R
2 августа 2017 в 14:38
0

@CodeConfident Переменная index не влияет на результат случайного числа. Вы можете инициализировать его любым способом, не беспокоясь об изменении результата. Надеюсь это поможет.

charles-allen
2 августа 2017 в 14:41
0

Точно ... он совершенно не используется. Я бы инициализировал его непосредственно рандом: int index = rand.nextInt(i.Length);

Mark Storer
17 сентября 2019 в 18:24
0

Или совсем нет. int index; \n index = rand... если увлекаешься объявлениями и назначениями по разным линиям. Некоторые стандарты кодирования более строгие (и без видимой цели), чем другие.

avatar
TJ_Fischer
12 декабря 2008 в 18:35
1473

Обратите внимание, что этот подход более пристрастен и менее эффективен, чем подход nextInt, https://coderhelper.com/a/738651/360211

Стандартный шаблон для выполнения этого:

Min + (int)(Math.random() * ((Max - Min) + 1))

Java Математическая библиотечная функция Math.random () генерирует двойное значение в диапазоне [0,1). Обратите внимание, что в этот диапазон не входит 1.

Чтобы сначала получить определенный диапазон значений, вам нужно умножить на величину диапазона значений, который вы хотите охватить.

Math.random() * ( Max - Min )

Возвращает значение в диапазоне [0,Max-Min), куда не входит «Макс-Мин».

Например, если вы хотите [5,10), вам нужно охватить пять целочисленных значений, поэтому вы используете

Math.random() * 5

Это вернет значение в диапазоне [0,5), где 5 не включено.

Теперь вам нужно сместить этот диапазон до диапазона, на который вы нацеливаетесь. Для этого нужно добавить значение Min.

Min + (Math.random() * (Max - Min))

Теперь вы получите значение в диапазоне [Min,Max). Следуя нашему примеру, это означает [5,10):

5 + (Math.random() * (10 - 5))

Но это все еще не включает Max, и вы получаете двойное значение. Чтобы включить значение Max, вам нужно добавить 1 к параметру диапазона (Max - Min), а затем усечь десятичную часть, приведя к типу int. Это достигается через:

Min + (int)(Math.random() * ((Max - Min) + 1))

Вот и все. Случайное целое число в диапазоне [Min,Max] или, как в примере [5,10]:

5 + (int)(Math.random() * ((10 - 5) + 1))
Lilian A. Moraru
23 февраля 2012 в 23:26
86

В документации Sun прямо говорится, что вам лучше использовать Random (), если вам нужен int вместо Math.random (), который производит double.

weston
29 декабря 2016 в 13:35
6

На самом деле это предвзято по сравнению с методами nextInt coderhelper.com/a/738651/360211

Cephalopod
29 августа 2019 в 09:48
6

"Смещенный" в этом случае означает, что после 2 ^ 53 казней у некоторых номеров в среднем будет одно дополнительное появление.

Tobias
20 октября 2020 в 13:28
0

Даже подумав, что я тоже использую это, я хочу указать, что это не настоящее случайное число. Вот почему его не следует использовать для каких-либо функций безопасности. Но для любых случайных случаев это самый простой способ.

avatar
Bill the Lizard
12 декабря 2008 в 18:31
116

Второй пример кода можно изменить на:

Random rn = new Random();
int range = maximum - minimum + 1;
int randomNum =  rn.nextInt(range) + minimum;
avatar
user2427
12 декабря 2008 в 18:28
19
int random = minimum + Double.valueOf(Math.random()*(maximum-minimum )).intValue();

Или взгляните на RandomUtils из Apache Commons.

zakmck
30 января 2015 в 09:27
0

Это полезно, но будьте осторожны с небольшим недостатком: сигнатуры методов похожи на: nextDouble (double startInclusive, double endInclusive), но если вы посмотрите внутрь методов, endInclusive на самом деле должен быть endExclusive.

Holger
3 июня 2016 в 09:47
0

Double.valueOf(Math.random()*(maximum-minimun)).intValue() - довольно запутанный (и неэффективный) способ сказать (int)(Math.random()*(maximum-minimun))

Hrishikesh Mishra
26 декабря 2016 в 05:14
0

Несоответствие орфографии минимальному возвращаемому минимуму + Double.valueOf (Math.random () * (максимум - минимум)). IntValue ();

avatar
Chinnery
12 декабря 2008 в 18:27
34

Интересно, подойдет ли какой-либо из методов генерации случайных чисел, предоставляемых библиотекой Apache Commons Math, всем этим требованиям.

Например: RandomDataGenerator.nextInt или RandomDataGenerator.nextLong

avatar
Michael Myers
12 декабря 2008 в 18:25
30
 rand.nextInt((max+1) - min) + min;
avatar
Greg Case
12 декабря 2008 в 18:25
4054

В Java 1.7 или более поздней версии стандартный способ сделать это следующий:

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);

См. соответствующий JavaDoc. Преимущество этого подхода в том, что нет необходимости явно инициализировать экземпляр java.util.Random, который может быть источником путаницы и ошибок при неправильном использовании.

Однако, наоборот, нет способа явно установить начальное значение, поэтому может быть сложно воспроизвести результаты в ситуациях, когда это полезно, например, при тестировании или сохранении игровых состояний и т. Д. В таких ситуациях можно использовать метод до Java 1.7, показанный ниже.

До версии Java 1.7 стандартный способ сделать это выглядит следующим образом:

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;
}

См. соответствующий JavaDoc. На практике класс java.util.Random часто предпочтительнее java.lang.Math.random ().

В частности, нет необходимости заново изобретать колесо генерации случайных целых чисел, когда в стандартной библиотеке есть простой API для выполнения задачи.

Daniel
12 августа 2014 в 10:34
47

Для вызовов, где значение max равно Integer.MAX_VALUE, возможно переполнение, в результате чего будет java.lang.IllegalArgumentException. Вы можете попробовать: randInt(0, Integer.MAX_VALUE). Кроме того, если nextInt((max-min) + 1) возвращает самое высокое значение (довольно редко, я полагаю), не будет ли оно снова переполняться (предположим, что min и max - достаточно высокие значения)? Как справляться с подобными ситуациями?

Moishe Lipsker
17 июня 2015 в 17:18
1

@momo класс RANDOM поддерживает nextLong. Вы можете использовать это вместо nextInt для длинных позиций.

mmm
17 июня 2015 в 18:42
3

@MoisheLipsker Должно быть, nextLong не принимает привязку как nextInteger

b1nary.atr0phy
18 августа 2015 в 01:01
1

@momo Заручитесь помощью по телефону double. Просто так: long val = ((long) (r.nextDouble() * (max - min))) + min

mmm
18 августа 2015 в 12:01
1

Да, я уже делаю это, используя Math.random (), который делает это: public static long random (long min, long max) {return min + Math.round (Math.random () * ((max - min)) ); }

leventov
4 сентября 2015 в 09:07
0

Этот фрагмент (который, вероятно, копируют тысячи людей) - ПЛОХОЙ. Он производит мусор. Просто ThreadLocalRandom.current().nextInt(min, max).

Greg Case
11 сентября 2015 в 01:57
14

@leventov ThreadLocalRandom был добавлен в Java через 2 1/2 года после того, как этот вопрос был впервые задан. Я всегда твердо придерживался мнения, что управление экземпляром Random выходит за рамки вопроса.

Greg Case
12 октября 2015 в 04:51
2

@AbhishekSingh Комментарии пытаются решить эту проблему, но более подробно: nextInt (N) возвращает число от 0 до N - 1, то есть никогда не вернет N в результате. В этом случае мы хотим включить N в наш возможный диапазон значений, поэтому мы добавляем единицу: nextInt (N + 1) => возвращает число в диапазоне от 0 до N, включая как 0, так и N.

Webserveis
3 октября 2016 в 19:55
6

В Android Random rand = new Random ();

Greg Case
4 октября 2016 в 00:29
6

@Webserveis Это рассматривается в комментариях к примеру. Краткая версия - вы не должны = new Random () для каждого вызова функции, иначе ваши результаты не будут достаточно случайными во многих случаях.

Chit Khine
7 марта 2017 в 08:02
1

Разве вы не должны инициализировать rand = new Random ()?

Greg Case
13 марта 2017 в 03:09
5

@ChitKhine Не при каждом вызове функции. Алгоритм RNG под капотом Random работает хорошо (достаточно для некриптографических приложений) при генерации последовательных случайных чисел. Однако, если экземпляр Random воссоздается при каждом вызове, это означает, что вместо правильного RNG вы будете получать «случайные» числа на основе того, какое начальное число выбирается каждый раз - часто это основано на системных часах. Это может дать явно неслучайные результаты. Вместо этого вам следует рассмотреть возможность создания экземпляра Random вне области действия метода. Пример кода пытается решить эту проблему.

user5365075
20 февраля 2018 в 13:04
0

Используйте ThreadLocalRandom.current().nextBytes(chunk);, если хотите сохранить себе new Random(). Благодаря очень популярный вопрос о генерации случайных целых чисел в Java.

Aman
14 ноября 2018 в 13:19
0

и если вы используете для Android java ThreadLocalRandom.current (). nextInt (1, 100), для этого требуется минимальный уровень API 21

avatar
krosenvold
12 декабря 2008 в 18:25
180

Использование:

minimum + rn.nextInt(maxValue - minvalue + 1)