1

I have to generate an eleven digit ID number but when I use random package, it says that it is out of range, so how can I make it eleven?

public static int generateID(){

    Random r = new Random();
    int numbers = 1000000000 + (int)(r.nextDouble() * 999999999);

    return numbers;
}
Stefan Falk
  • 23,898
  • 50
  • 191
  • 378
Ekin
  • 37
  • 1
  • 2
  • 9

5 Answers5

4

To ensure uniform distribution, you should use the nextInt(int bound) method.

Since it cannot generate 11 digit numbers (exceeds capacity of int), you need to call it twice, e.g. to get last 9 digits (000000000-999999999), and first 2 digits (10-99).

Remember to use long somewhere to prevent int overflow.

long numbers = r.nextInt(1_000_000_000)               // Last 9 digits
             + (r.nextInt(90) + 10) * 1_000_000_000L; // First 2 digits
Andreas
  • 154,647
  • 11
  • 152
  • 247
4
import java.util.concurrent.ThreadLocalRandom;
...
public long generateId() {
  ThreadLocalRandom random = ThreadLocalRandom.current();
  return random.nextLong(10_000_000_000L, 100_000_000_000L);
}

Use the right tool. In this case, Random is worth much less than ThreadLocalRandom.

Olivier Grégoire
  • 33,839
  • 23
  • 96
  • 137
  • You wonder why they never added the extra methods to `Random` to keep them consistent. Seems they considered `Random` to be obsolete, i.e. don't bother to keep up-to-date, without actually marking it obsolete. *What were they thinking?!?!?* – Andreas Oct 13 '17 at 20:50
  • @Andreas Yeah, I'm still wondering why they didn't rewrite `Random` to use the same methods. It's just plain wrong... – Olivier Grégoire Oct 13 '17 at 20:59
  • in addition to that question how can I write a code that each ID number will be unique – Ekin Oct 18 '17 at 18:40
  • @EKIN The only way would be to put all your ids in a `Set` and check if one ID is contained in that set. – Olivier Grégoire Oct 18 '17 at 18:52
  • is there any chance we can put it on a for loop or something else rather than set – Ekin Oct 22 '17 at 15:26
2

Here :

int numbers = 1000000000 + (int)(r.nextDouble() * 999999999);

r.nextDouble() * 999999999 produces a number with 8 digits.
Additioning 1000000000 that contains 10 digits to a number that contains 8 digits will never produce a number that contains 11 digits.

Besides, 11 digits requires a long not an int as Integer.MAX_VALUE == 2147483647 (10 digits).

To get a 11 digits number, you can do :

 long n = 10000000000L + ((long)rnd.nextInt(900000000)*100) + rnd.nextInt(100);

((long)rnd.nextInt(900000000)*100) + rnd.nextInt(100) returns a number between 0 and 89 999 999 999.
Additionating this number to 10 000 000 000 will produce a number with 11 digits between 0 and 99 999 999 999.

For example, try that :

public static long generateID() {
      return 10000000000L + ((long)rnd.nextInt(900000000)*100) + rnd.nextInt(100);
}
davidxxx
  • 125,838
  • 23
  • 214
  • 215
  • It is still make 10 digits – Ekin Oct 13 '17 at 20:04
  • Numbers below `10000000000`, i.e. `0` to `9999999999`, are not actually 11 digit numbers. – Andreas Oct 13 '17 at 20:38
  • Im referring to `(long) (Math.random() * 100_000_000_000L)` resulting in numbers between `0` and `99_999_999_999` (inclusive), but 10% of those numbers are not 11 digits long, e.g. `42` is only 2 digits. – Andreas Oct 13 '17 at 20:45
  • 1
    @davidxxx that's worse than previously... The number 10000000000L has 10% chance to be drawn, while each other has roughly 0.000000001%... -_-' – Olivier Grégoire Oct 13 '17 at 20:54
1

The maximum value of a Java 'int' is 2147483647. Ten digits, and only 9 unless you constrain it below that value.

There are several ways to handle this, but the easiest would be to use the datatype 'long' instead of 'int'. The max value of a 'long' is 19 digits, and should support your use case.

HumanJHawkins
  • 240
  • 2
  • 9
0

Use a long. Like this:

public static int generateID(){

    Random r = new Random();
    long numbers = 1000000000L + (long)(r.nextDouble() * 999999999L);

    return numbers;
}

The “L” are to explicitly tell the compiler that we want longs, not ints.

Steampunkery
  • 3,839
  • 2
  • 19
  • 28
  • Actually, if you do not use `L` with this big number, then compiler say you himself that you are not right! – Oleg Cherednik Oct 13 '17 at 20:23
  • Right. We tell the compiler to use longs – Steampunkery Oct 13 '17 at 20:25
  • `(long)(r.nextDouble() * 999999999L)` gives numbers between `0` and `999999998` (inclusive). Adding `1000000000L` gives numbers between `1000000000` and `1999999998`. That is only 10 digits, not 11 digits as requested in question, and it's not even the full range of 10 digit numbers. – Andreas Oct 13 '17 at 20:32
  • you need to add a zero to make it generate 11 digit – InCh Jul 09 '19 at 15:36