While looking for best attempts at generating truly random numbers, I stumbled upon this code example.
Looking for opinions on this snippet.
using System;
using System.Security.Cryptography;
private static int NextInt(int min, int max)
{
RNGCryptoServiceProvider rng = new RNGCryptoServiceProvider();
byte[] buffer = new byte[4];
rng.GetBytes(buffer);
int result = BitConverter.ToInt32(buffer, 0);
return new Random(result).Next(min, max);
}
Source: http://www.vcskicks.com/code-snippet/rng-int.php
Would this be preferred over using a tick count seed such as:
Random rand = new Random(Environment.TickCount);
rand.Next(min, max);
Note:
I am not looking for third party random data providers such as Random.org, as such a dependency is not realistic to the application.
I think this is a more efficient, and possibly faster generator then the ones listed above..
Don't use your code. Your solution is wrong and generates poor random numbers. I suggest my solution, which generates cryptographically strong random numbers:
It really depends on the intended use or requirement of the random number being generated.
The Random class is useful for practical randomization like randomizing the order images display in an image rotator or rolls of a die.
If, on the other hand, you need random numbers requiring a greater amount of security, like to generate a password or payment confirmation key, then using a class such as RNGCryptoServiceProvider or creating your own implementation of the abstract class RandomNumberGenerator that implements a cryptographic algorithm are better alternatives.
I asked a similar question 2 years back :) check and see if it helps you. I used that code for generating a secure random number for payment processing.
Well, using
RNGCryptoServiceProvider
gives you an unguessable crypto-strength seed whereasEnvironment.TickCount
is, in theory, predictable.Another crucial difference would be evident when calling your
NextInt
method several times in quick succession. UsingRNGCryptoServiceProvider
will seed theRandom
object with a different crypto-strength number each time, meaning that it will go on to return a different random number for each call. UsingTickCount
risks seeding theRandom
object with the same number each time (if the method is called several times during the same "tick"), meaning that it will go on to return the same (supposedly random) number for each call.If you genuinely need truly random numbers then you shouldn't be using a computer to generate them at all: you should be measuring radioactive decay or something similarly, genuinely unpredictable.
Ok, so I'm a little late to the party, but I really wanted a full implementation of System.Random that can be called multiple times during the same timer tic and yield different results. After much agonizing over different implementations, I settled on the simplest one that I came up with, which provides a default constructor that supplies a random key to the base System.Random constructor:
Along the way, I also wrote and tested an implementation that overrides the methods necessary to use RNGCryptoServiceProvider to provide ALL of the random values (rather than relying on whatever random number generator is baked into the System.Random class). But I have no idea how cryptographically strong the results are by the time you take my random Sample() values and push 'em through the transformations to produce integer values. Anyway, here is the code if anyone wants it: