随机数生成器(Random)的误用

很久以前发在公司内网的文章,发出来共享,隐去具体项目、人员的名字。

某日查一个bug,发现类似下面的代码
class Generator
{
...
private StringBuffer generateRandStr(String strSet,int length)
{
StringBuffer sbuf = new StringBuffer() ;
int charsetSize = strSet.length();
Random random = new Random();
for( int i = 0 ; i < length ; i++ )
{
//选择一个字符
int index = random.nextInt( charsetSize ) ;
char c = strSet.charAt(index);
sbuf.append( c ) ;
}
return sbuf;
}
...
}

这是一段生成随机字符串的程序,用于生成密码等场合,代码很简单也很清晰,但这里隐藏这一个bug,现象是连续多次调用这个方法产生的结果很多时候是相同的,如果传入的参数一样的话。
原因是什么呢?看到Random,我想到了伪随机数的问题,我们知道计算机算出的随机数通常称之为伪随机数,因为它实际上并不是完全随机的,只要确定了算法和种子,那么产生的随机数是固定的序列,再看一下Random的javadoc就更清楚了:
An instance of this class is used to generate a stream of pseudorandom numbers. The class uses a 48-bit seed, which is modified using a linear congruential formula. (See Donald Knuth, The Art of Computer Programming, Volume 2, Section 3.2.1.)

If two instances of Random are created with the same seed, and the same sequence of method calls is made for each, they will generate and return identical sequences of numbers.

如果连续调用发生在同一毫秒内,就意味着创建的随机数发生器的种子相同,那么结果就是相同的。养成阅读javadoc的习惯可以减少很多出错的机会。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值