"Resetting" the seed pseudo-random number generator multiple times?

A friend of mine today thought about creating a pseudo-random number generator seed several times using a pseudo-random number generated in order to "make things more randomized."

Example in C #:

// Initiate one with a time-based seed
Random rand = new Random(milliseconds_since_unix_epoch());
// Then loop for a_number_of_times...
for (int i = 0; i < a_number_of_times; i++)
{
    // ... to initiate with the next random number generated
    rand = new Random(rand.Next());
}
// So is `rand` now really random?
assert(rand.Next() is really_random);

      

But I thought it could probably increase the chances of getting a re-seed for the pseudo-random number generator.

Will it be

  • make things more randomized,
  • by making it scroll a certain amount of seeds, or
  • does nothing for randomness (i.e. does not increase or decrease)?

Can some pseudo-random number generator provide detailed explanations so that I can convince my friend? I would be glad to see answers explaining further details in the pseudo-random number generation algorithm.

+2


source to share


3 answers


There are three main levels of use for pseudo-random numbers. Each level falls under the one below.

  • Unexpected numbers without much correlation guarantees. Generators at this level usually have some hidden correlations that may or may not matter to you.
  • Statistically independent number with known correlation. They are usually required for numerical simulations.
  • Cryptographically secure numbers that cannot be guessed. They are always needed when security is a problem.

Each of them is deterministic. A random number generator is an algorithm that has some internal state. By applying the algorithm, you will get a new internal state and output number. Additive generator means tuning the internal state; it is not always the case that the seed interface allows customization of all possible internal states. As a general rule of thumb, always assume that the standard random () library only works at its weakest level, level 1.



To answer your specific question, the algorithm in question (1) cannot increase randomness and (2) can decrease it. The expectation of randomness is thus strictly lower than sowing it once at the beginning. The reason comes from the possible existence of short iterative loops... The iterative loop for the function F

is a pair of integers n

and k

, where F^(n) (k) = k

, where the exponent is the number of times F

. Eg F^(3) (x) = F(F(F(x)))

. If there is a short iteration cycle, the random numbers will repeat more often than otherwise. In the presented code, the iteration function is to seed the generator and then draw the first output.

To answer a question you didn't quite ask, but which has something to do with understanding this, seeding with a millisecond counter makes your generator fail at level 3, indescribability. This is because the number of possible milliseconds is cryptographically small , which is a number known to be searchable. At the time of this writing, 2 ^ 50 should be considered cryptographically small. (For what is considered cryptographically large in any year, please find a reputable expert.) Now the number of milliseconds per century is approximately 2 ^ (41.5), so don't use this form of seeding for security purposes.

+5


source


Your example will not increase randomness because there is no increase in entropy . It is simply derived from the program runtime.

Instead of using something based on current time, computers maintain an entropy pool and create it statistically random (or at least unidentified) data. For example, the time delay between network packets or keystrokes, or the time it takes to read a hard disk.



You should use this entropy pool if you want good random numbers. They are known as Cryptographically Secure Pseudo-Random Number Generators .

In C #, see Cryptography.RandomNumberGenerator Class to get a safe random number.

+1


source


It won't make things more "random".

Our seed defines a random but completely definite sequence of numbers that rand.next () gives us.

Instead of making things more random, your code defines a mapping from your initial seed to some final seed and given the same initial seed, you will always have the same final seed.

Try playing with this code and you will see what I mean (also, here is a link to a version that you can run in your browser ):

int my_seed = 100; // change my seed to whatever you want
Random rand = new Random(my_seed);
for (int i = 0; i < a_number_of_times; i++)
{
    rand = new Random(rand.Next());
}
// does this print the same number every run if we don't change the starting seed?
Console.WriteLine(rand.Next()); // yes, it does

      

A random object with this final seed is like any other random object. It took more time to create it.

0


source







All Articles