问题描述
我创建了一个骰子游戏,其中骰子基于1-100的百分位数.
I've created a dice game where the dice is based on a percentile, 1-100.
public static void Roll()
{
Random rand = new Random((int)DateTime.Now.Ticks);
return rand.Next(1, 100);
}
但是我不认为这是基于当前时间的真正随机值.
But I don't feel like it's a real random based on current time.
如果我这样做
for (int i = 0; i < 5; i++)
{
Console.WriteLine("#" + i + " " + Roll());
}
它们都是相同的值,因为DateTime.Now.Ticks
不变,因此种子相同的数字.
They would all be the same values, because the DateTime.Now.Ticks
didn't change, it seeded the same number.
我本来以为如果当前时间种子相同,那么我可以生成一个新的随机种子,但是感觉不像是诚实的重新滚动"
I was thinking I could generate a new random seed if the seed was the same due to the current time, but it doesn't feel like an honest "re-roll"
我应该怎么做才能复制接近真实/诚实的骰子骰?我应该使用RNGCryptoServiceProvider
类代替吗?
What should I do to try and replicate a close to real/honest dice roll? Should I use the RNGCryptoServiceProvider
class to generate rolls instead?
推荐答案
DateTime.Now.Ticks
的分辨率仅为大约16ms ,因此,如果您创建的Random
在16ms的时隙"中多次过载,则它们都是用相同的值播种,因此您将获得相同的序列.
DateTime.Now.Ticks
only has a resolution of approximately 16ms, so if you create a Random
with that overload multiple times within a 16ms "slot" they will all be seeded with the same value and therefore you will get the same sequence.
在循环外初始化Random
以便生成单个Random
序列,而不是每次在循环内创建它都可能导致Randoms
用相同的值播种并产生相同的序列
Initialize your Random
outside your loop so that a single Random
sequence is produced, rather than creating it each time within the loop which could result in Randoms
being seeded with the same value and so produce the same sequence.
更新
我先前的观点是,默认构造函数使用CPU ticks初始化了Random
,这是不正确的,默认构造函数实际上使用了 Environment.TickCount ,即:
My previous point that the default constructor initialized Random
with CPU ticks was incorrect, the default constructor actually uses Environment.TickCount which is:
哪个分辨率仍然较低.如果快速连续创建多个Random
实例,则可以在同一时隙内轻松创建它们,因此它们具有相同的种子值,并创建相同的序列.创建Random
的单个实例并使用它.
Which still has a low resolution. If you make multiple instances of Random
in quick succession, they can easily be created within the same time slot and therefore have the same seed value, and create the same sequence. Create a single instance of Random
and use that.
更新
在您的评论之前,如果您希望跨多个线程生成随机序列,请参阅下面的Jon Skeet文章,其中讨论了线程安全包装器:
Further to your comments, if you wish to generate a random sequence across multiple threads, please see the following Jon Skeet article which discusses a thread-safe wrapper:
https://codeblog.jonskeet.uk/2009/11/04/重访随机性
这篇关于创建一个真正的随机的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!