2016-05-13 180 views
6

今天我遇到了這個問題,我確信有一個優雅的解決方案,我沒有想到。生成一個具有指定位數的隨機整數Java

比方說,我想用一個指定的位數生成一個Java中的隨機整數(或長整數),這個位數可以改變。

I.e.將一些數字傳入一個方法,並返回一個具有指定位數的隨機數。例如,N = 3,產生一個介於100-999之間的隨機數; N = 4,產生1000-9999

private long generateRandomNumber(int n){ 

/*Generate a random number with n number of digits*/ 

} 

我嘗試到目前爲止之間的隨機數(這個作品,但似乎凌亂)

private long generateRandomNumber(int n){ 

    String randomNumString = ""; 

    Random r = new Random(); 

    //Generate the first digit from 1-9 
    randomNumString += (r.nextInt(9) + 1); 

    //Generate the remaining digits between 0-9 
    for(int x = 1; x < n; x++){ 
     randomNumString += r.nextInt(9); 
    } 

    //Parse and return 
    return Long.parseLong(randomNumString); 

} 

是否有比這更好/更高效的解決方案?

*在指定範圍內生成隨機數有很多解決方案,我更加好奇在給定一定數量的數字的情況下生成隨機數的最佳方法,以及使解決方案足夠健壯以處理任意數量數字。

我不希望有一個最大和最小傳遞,而只是位數需要

+2

我喜歡你的方法,因爲它沒有受到LONG長度的約束,除了你長時間施展它。 – Elye

+0

@aetheria更新,以顯示它爲什麼不是重複 –

+0

@aetheria你能解釋爲什麼這是一個重複?這是一個完全不同的問題,比你引用 –

回答

8
private long generateRandomNumber(int n) { 
    long min = (long) Math.pow(10, n - 1); 
    return ThreadLocalRandom.current().nextLong(min, min * 10); 
} 

nextLong在下限包含和上限排他性之間產生隨機數,所以用參數(1_000, 10_000)來調用它,例如結果是數字1000到9999. 舊的Random不幸的是沒有得到那些不錯的新功能。但基本上沒有理由繼續使用它。

+0

啊。我錯過了這個方法,雖然它使用了相同的邊界檢查思路:while(r = bound)' –

+0

我不知道ThreadLocalRandom。你是否建議一般使用這種隨機數生成? –

+0

@TonyScialo是的。 http://stackoverflow.com/questions/23396033/random-over-threadlocalrandom(這是除非你需要安全的隨機) – zapl

2

您可以忽略不在所要求的範圍內的號碼。這樣修改後的僞隨機數發生器保證它隨機均勻產生在給定範圍內的數字:

public class RandomOfDigits { 
    public static void main(String[] args) { 
     int nd = Integer.parseInt(args[0]); 
     int loIn = (int) Math.pow(10, nd-1); 
     int hiEx = (int) Math.pow(10, nd); 
     Random r = new Random(); 
     int x; 
     do { 
      x = r.nextInt(hiEx); 
     } while (x < loIn); 
     System.out.println(x); 
    } 
} 
+0

'int x = loIn + r.nextInt(hiEx-loIn)'會更好。 – andrucz

+0

這是爲什麼?我嘗試了一百萬次迭代,我的PRNG似乎傾向於平均值。也許我應該嘗試更多... –

3
public static int randomInt(int digits) { 
    int minimum = (int) Math.pow(10, digits - 1); // minimum value with 2 digits is 10 (10^1) 
    int maximum = (int) Math.pow(10, digits) - 1; // maximum value with 2 digits is 99 (10^2 - 1) 
    Random random = new Random(); 
    return minimum + random.nextInt((maximum - minimum) + 1); 
} 
0

這是我自然會寫這樣的方法方式:

private long generateRandomNumber(int n){ 
    double tenToN = Math.pow(10, n), 
      tenToNMinus1 = Math.pow(10, n-1); 
    long randNum = (long) (Math.random() * (tenToN - tenToNMinus1) + tenToNMinus1); 
    return randNum; 
}