Java中,除了使用 java.util.Random 生成随机数之外,还有几种其他常见的方法可以生成随机数,如使用 Math.random()、ThreadLocalRandom 和 SecureRandom等。本文主要介绍Java生成随机数的方法,比java.util.Random生成的随机数效果更好一些。

1、使用单独的方法生成随机数代码

根据给定的 BigInteger 随机索引生成一个排列(Permutation),并且通过阶乘的除法和余数来逐步构造最终的排列。

import java.math.BigInteger;
import java.util.Arrays;

public class Main {

    public static int[] shuffle(int n, BigInteger random_index) {
        int[] perm = new int[n];
        BigInteger[] fact = new BigInteger[n];
        fact[0] = BigInteger.ONE;

        // 计算阶乘
        for (int k = 1; k < n; ++k) {
            fact[k] = fact[k - 1].multiply(BigInteger.valueOf(k));
        }
        // 根据 random_index 和阶乘数组生成排列
        for (int k = 0; k < n; ++k) {
            BigInteger[] divmod = random_index.divideAndRemainder(fact[n - 1 - k]);
            perm[k] = divmod[0].intValue();
            random_index = divmod[1];
        }

        // 重新调整排列值,确保排列顺序正确
        for (int k = n - 1; k > 0; --k) {
            for (int j = k - 1; j >= 0; --j) {
                if (perm[j] <= perm[k]) {
                    perm[k]++;
                }
            }
        }
        return perm;
    }

    public static void main(String[] args) {
        System.out.printf("%s\n", Arrays.toString(
            shuffle(50, new BigInteger(
                "7890123456789012345678901234567890123456789012345678901234567890"))));
    }
}

2、使用SecureRandom生成随机数

SecureRandom 是用于生成安全的随机数,通常用于密码学应用,它比 Random 更加复杂和安全。

import java.security.SecureRandom;

public class Main {
    public static void main(String[] args) {
        SecureRandom secureRandom = new SecureRandom();

        // 生成一个 [0, 100) 之间的随机整数
        int randomInt = secureRandom.nextInt(100);
        System.out.println("Random integer [0, 100) using SecureRandom: " + randomInt);

        // 生成一个 [0.0, 1.0) 之间的随机浮动数
        double randomDouble = secureRandom.nextDouble();
        System.out.println("Random double [0.0, 1.0) using SecureRandom: " + randomDouble);
    }
}

3、使用 ThreadLocalRandom

ThreadLocalRandom 是在多线程环境中生成随机数的推荐方法,能够避免 Random 对象的竞争。它通过线程局部变量来提供性能上的优势。

import java.util.concurrent.ThreadLocalRandom;

public class Main {
    public static void main(String[] args) {
        // 生成一个 [0, 100) 之间的随机整数
        int randomInt = ThreadLocalRandom.current().nextInt(100);
        System.out.println("Random integer [0, 100) using ThreadLocalRandom: " + randomInt);

        // 生成一个 [0.0, 1.0) 之间的随机浮动数
        double randomDouble = ThreadLocalRandom.current().nextDouble();
        System.out.println("Random double [0.0, 1.0) using ThreadLocalRandom: " + randomDouble);
    }
}

推荐文档