3 Examples to Generate Random Integers on a Range in Java

Manytimes you need to generate random numbers, particular integers in a range but unfortunately, JDK doesn't provide a simple method like nextIntegerBetween(int minInclusive, int maxExclusive), because of that many Java progarmmers, particularly beginners struggle to generate random numbers between a range e.g. random integers between 1 to 6 if you are creating a game of dice, or random number between 1 to 52 if you are creating a game of playing cards and you need to choose a random card, or most commonly random numbers between 1 to 10 and 1 to 100. Then, the question comes, how to solve this problem? How to generate random int values between a range? Well, you need to do a little bit of work.

Even though JDK doesn't provide a simple solution, it provides all the tools you need to generate those random numbers.  The support of random numbers exists from JDK 1 via Math.random() method which returns a random number, albeit a floating point value, a double between 0 and 1.

If you are good in maths you can use that method to generate a random number between any range, but that's not the best approach, particularly if you need integer values and not the float or double.

The next and suggested approach is to use the java.util.Random class which generates random numbers and provides methods to generate a random integer, long, float, double and even boolean values. You can use the nextInt() method to generate random integers. Though, you also need to apply a little bit of Mathematics to generate random integers between two numbers.


The third and probably the best approach to generate random integers in a range is to use a general-purpose Java library like Apache Commons Lang, which provides a class called RandomUtils. This has a method public static int nextInt(int startInclusive, int endExclusive), which returns a random integer within the specified range.

If you need random numbers for a real-world project, I would suggest using this function and library, instead of re-inventing the wheel, as suggested in Effective Java 3rd Edition by Joshua Bloch.

In this article, I'll go through each of these approaches apart from the Math.random() and we'll see code examples to generate random numbers in a range e.g. 1 to 10 or 1- 52 or 1- 6 etc.



Generating Random integers between 1 to 6 using java.util.Random

The first and common way to generate random numbers e.g. integers or long is by using the java.util.Random class. This method provides methods like nextInt() or nextLong() to get the random int or long value.

If you need random integer in a range then we need to use the overloaded nextInt(int bound) method which returns a random integer between 0 (inclusive) and bound (exclusive), bound is nothing but the maximum value in your range.

In order to generate a random value between a range e.g. 1 to 6, we can apply a little bit of maths as shown below:

/**
*
* @param start - the first number in range
* @param end - last or maximum number in range
* @return - a random number in the range
*/
public static int getRandomInRange(int start, int end){
   return start + generator.nextInt(end - start + 1);
}


So, for example, if you need random integer between 5 and 10 you can do something like:

int random = 5 + Random.nextInt(10 - 5 + 1);

or

int random = 5 + Random.nextInt(6)

Since nextInt() will return an integer between 0 and 6 (exclusive) the maximum value returned by this would between 0 and 5 and by adding 5 you get the random value between 5 and 10.

The generator in above utility method is an instance of java.util.Random class, which is encapsulated in a class level variable because it's not advisable to generate an instance of java.util.Random every time you need a random number. You can reuse the same instance for better performance.



Random Integers in a range using ThreadLocalRandom of JDK7

If you are running in JDK 7 or JDK 8 or maybe on JDK 9 then you can use the class ThreadLocalRandom from Java 7 to generate random numbers in Java. This class is equivalent to java.uti.Random in a concurrent environment.

 It's more efficient because random numbers are generated locally on each thread and it's preferred approach on a multi-threaded application. You can assume that each Thread kept their own random number generator inside a ThreadLocal variable.

This class provides a method like what I have described in the opening phrase e.g. nextInt(origin, bound), which returns a pseudorandom int value between the specified origin (inclusive) and the specified bound (exclusive). This is probably the easiest way to generate random int values between a range in Java without using an external, third-party library.

Here is the code example to use ThreadLocalRandom to generate random integers between 1 to 10 in Java:

int randomBetweenOneTo100 = ThreadLocalRandom
                              .current()
                              .nextInt(1, 10 + 1);

Since the bound is exclusive you need to increase the range by + 1. For example to generate int values between 1 to 10, you need to call nextInt(1, 10 + 1) or nextInt(1, 11).

Similarly, if you need random integers between 5 and 10 then you need to call nextInt(5, 11) because 5 is inclusive but 11 is exclusive, this will return any value between 5 and 10.

Btw, if you want to learn more about ThreadLocalRandom and ThreadLocal variable in Java, I suggest you go through Complete Java 9 Masterclass, which covers this and other important concepts of Java.

How to Generate Random Integers on a Range in Java


Random Int values in a specified range using RandomUtils of Apache Commons

The third and probably the best way to generate random int values in a given range is by using the nextInt(int startInclusive, int endExclusive) of RandomUtils class from Apache Commons Lang 3.4.

This method is similar to the nextInt(int origin, int bound) of JDK 7 ThreadLocalRandom but good thing is that you can use it on your application even if you are not running on Java 7 e.g. still running on Java SE 6.

I generally follow advice from Effective Java, particularly the one about using tried and tested library instead of creating your own stuff for common things and that's why I always include this library in my project.

3 Ways to Generate Random Numbers on a Range in Java


Here is an example to use this method to generate random integers in a range e.g. between 1 and 52 to randomly choose a card in a pack of playing cards:

int random = RandomUtils.nextInt(1, 52 + 1);

As the name suggests it returns int values for given range but only start is inclusive. Since the bound is exclusive, you probably need to increase the range by 1 to get the values exactly between the range.



Java Program to generate random numbers between a range

Now that, you understand the different ways to generate random numbers in a Java, particularly in a specified range, let's see a complete Java program which uses these methods to actually generate random values and display it on a console.

import java.util.Random;
import java.util.concurrent.ThreadLocalRandom;
import org.apache.commons.lang3.RandomUtils;

public class HelloWorld {

  private static final Random generator = new Random();

  public static void main(String[] args) {

    // code to generate random number between 1 to 10
    // using ThreadLocal

    System.out.println("generating random number in range"
        + " ( 1- 10) using ThreadLocalRandom");

    for (int i = 0; i < 10; i++) {
      int randomBetweenOneTo100 = ThreadLocalRandom
                                    .current()
                                    .nextInt(1,10 + 1);
      System.out.print(randomBetweenOneTo100 + " ");
    }
    System.out.println();

    // using java.util.Random
    System.out.println("generating random number in range"
            + " (1 -52) using java.util.Random");

    for (int i = 0; i < 10; i++) {
      int random = getRandomInRange(1, 52);
      System.out.print(random + " ");
    }
    System.out.println();

    
    // 3rd and best approach - use Apache Commons RandomUtils
    System.out.println("generating random number in range "
        + "(1 -6) using Apache Commons RandomUtils");

    for (int i = 0; i < 10; i++) {
      int random = RandomUtils.nextInt(1, 7);
      System.out.print(random + " ");
    }
    System.out.println();

  }

  /**
   * @param start - the first number in range
   * @param end - last or maximum number in range
   * @return - a random number within given range
   */

  public static int getRandomInRange(int start, int end) {
    return start + generator.nextInt(end - start + 1);

  }

}

Output:
Generating a random number in the range ( 1- 10) using ThreadLocalRandom
9 2 3 1 10 5 7 7 10 4
Generating a random number in the range (1 -52) using java.util.Random
48 9 13 50 28 34 44 19 51 29
Generating a random number in the range (1 -6) using Apache Commons RandomUtils
6 6 4 2 3 3 1 5 5 1

You can see that in all examples, we have successfully generated int values which are in the specified range i.e. 1 to 10, 1 to 52, and 1 to 6. You can do the same to generate int values in the range you want.

3 Ways to Generate Random Integers in Java


Important points to Remember

Now that you know how to generate random numbers in Java, particularly random integers in between a range, let's revise some of the important points:

1) The Math.random() returns a double value between 0 and 1, which can be used to generate random integers but not suitable.

2) The preferred way to generate random integer values is by using the nextInt(bound) method of java.util.Random class. This method returns a pseudorandom, uniformly distributed int value between 0 (inclusive) and the specified value (exclusive). You can then tweak it to ensure values are in the specified range.


3) The JDK 7 introduced a new class called ThreadLocalRandom, which is equivalent to class java.util.Random for multithreaded environment. In this case, a random number is generated locally in each of the threads.

So we have a better performance by reducing the contention. If you want to know more about ThreadLocalRandom, I suggest you read The Definitive Guide to Java Performance by Scott Oaks, he has a very good write up on that topic.

3 Ways to Generate Random Integers on a Range in Java

4) The best way to generate random integers between a range is by using the RandomUtils class from Apache Commons Lang. This was added to a newer version of Apache commons lang and returns an integer value between two given numbers.

5) In order to use RandomUtils class, you need to include the commons-lang3-3.4.jar in your project's classpath or you need to import this dependency using Maven.


That's all about how to generate random numbers between a range. We have seen 3 ways to create random integer values between giving range e.g. between minimum and maximum. You can adjust the code to make sure that maximum is exclusive or inclusive. You can use any of three methods but I suggest you follow Joshua Bloch's advice of Effective Java, now updated for JDK 8 and 9, about using a library instead of creating your own methods and that's why the RandomUtils from Apache commons looks the best away along with ThreadLocalRandom from JDK 7.

Other Java tutorials and Resources you may like
Introduction to Java for Programmers
How to create a ZIP file in Java?
How to write to a file in Java?
How to append text into existing file in Java?
How to lock a file before writing in Java?
How to read from an Excel File in Java using Apache POI
Complete Java 9 Masterclass by Udemy

Thanks for reading this article so far. If you like these tutorials and my explanation then please share with your friends and colleagues. If you have any questions or feedback then please drop a comment. 

No comments:

Post a Comment