两次调用Random.nextInt()拼接生成long值是否概率均匀?
结论
你的判断是对的,这个方案确实能生成近似等概率的任意long值。
原理说明
- 按照JDK文档的约定,无参的
nextInt()方法本身就会近似等概率产出全部2^32种可能的int值,两次调用得到的是两个独立、均匀分布的32位整数。 - 两个独立的32位均匀随机数组合起来总共有2^32 * 2^32 = 2^64种可能,刚好覆盖long类型的全部取值范围。把两个数按高低位拼接成8字节的long之后,每个long值出现的概率自然也是近似相等的,和
nextInt()本身的等概率程度一致。
代码相关说明
你写的ByteBuffer实现逻辑没有问题,putInt()是按原始字节写入int内容的,不会被有符号整数的符号位扩展影响,最终拿到的long结果是符合预期的。只是这个写法有点冗余,完全可以不用ByteBuffer,直接用位运算就能实现一样的拼接效果,代码更轻量简洁:
Random r = new Random(); int firstPart = r.nextInt(); int secondPart = r.nextInt(); // 位运算拼接,注意做无符号处理避免int符号位干扰结果 long result = ((long) firstPart << 32) | (secondPart & 0xFFFFFFFFL);
补充说明:这里提到的「近似等概率」是和Random类本身的伪随机属性匹配的。Random本质是基于线性同余算法的确定性伪随机生成器,生成的序列存在可预测性和微小的统计偏差,不属于密码学安全的随机数实现,但完全符合文档描述的概率分布要求。
内容的提问来源于stack exchange,提问作者Trần Hoàn
相关产品推荐
相关产品推荐

