How to implement a pseudo random function - algorithm

I want to generate a sequence of random numbers that will be used to pick tiles for a "maze". Each maze will have an id and I want to use that id as a seed to a pseudo random function. That way I can generate the same maze over and over given it's maze id. Preferably I do not want to use a built in pseudo random function in a language since I do not have control over the algorithm and it could change from platform to platform. As such, I would like to know:
How should I go about implementing my own pseudo random function?
Is it even feasible to generate platform independent pseudo random numbers?

Yes, it is possible.
Here is an example of such an algorithm (and its use) for noise generation.
Those particular random functions (Noise1, Noise2, Noise3, ..) use input parameters and calculate the pseudo random values from there.
Their output range is from 0.0 to 1.0.
And there are many more out there (Like mentioned in the comments).
UPDATE 2019
Looking back at this answer, a better suited choice would be the below-mentioned mersenne twister. Or you could find any implementation of xorshift.

The Mersenne Twister may be a good pick for this. As you can see from the pseudocode on wikipedia, you can seed the RNG with whatever you prefer to produce identical values for any instance with that seed. In your case, the maze ID or the hash of the maze ID.

If you are using Python, you can use the random module by typing at the beginning,
import random. Then, to use it, you type-
var = random.randint(1000, 9999)
This gives the var a 4 digit number that can be used for its id
If you are using another language, there is likely a similar module

Related

Rust GSL library always returns the same number for a random number generator

I am using the rgsl library in Rust that wraps functions from the C GSL math libraries. I was using a random number generator function, but I am always getting the same exact value whenever I generate a new random number. I imagine that the number should vary upon each run of the function. Is there something that I am missing? Do I need to set a new random seed each time or such?
extern crate rgsl;
use rgsl::Rng;
fn main() {
rgsl::RngType::env_setup();
let t = rgsl::rng::default();
let r = Rng::new(&t).unwrap()
let val = rgsl::randist::binomial::binomial(&r, 0.01f64, 1u32);
print!("{}",val);
}
The value I keep getting is 1, which seems really high considering the probability of obtaining a 1 is 0.01.
The documentation for env_setup explains everything you need to know:
This function reads the environment variables GSL_RNG_TYPE and GSL_RNG_SEED and uses their values to set the corresponding library variables gsl_rng_default and gsl_rng_default_seed
If you don’t specify a generator for GSL_RNG_TYPE then gsl_rng_mt19937 is used as the default. The initial value of gsl_rng_default_seed is zero.
(Emphasis mine)
Like all software random number generators, this is really an algorithm that produces pseudo random numbers. The algorithm and the initial seed uniquely identify a sequence of these numbers. Since the seed is always the same, the first (and second, third, ...) number in the sequence will always be the same.
So if I want to generate a new series of random numbers, then I need to change the seed each time. However, if I use the rng to generate a set of random seeds, then I will get the same seeds each time.
That's correct.
Other languages don't seem to have this constraint, meaning that the seed can be manually set if desired, but is otherwise is random.
A classical way to do this is to seed your RNG with the current time. This produces an "acceptable" seed for many cases. You can also get access to true random data from the operating system and use that as a seed or mix it in to produce more random data.
Is there no way to do this in Rust?
This is a very different question. If you just want a random number generator in Rust, use the rand crate. This uses techniques like I described above.
You could even do something crazy like using random values from the rand crate to seed your other random number generator. I just assumed that there is some important reason you are using that crate instead of rand.

Is it possible to reverse a pseudo random number generator?

Is it possible to reverse a pseudo random number generator?
For example, take an array of generated numbers and get the original seed.
If so, how would this be implemented?
This is absolutely possible - you just have to create a PRNG which suits your purposes. It depends on exactly what you need to accomplish - I'd be happy to offer more advice if you describe your situation in more detail.
For general background, here are some resources for inverting a Linear Congruential Generator:
Reversible pseudo-random sequence generator
pseudo random distribution which guarantees all possible permutations of value sequence - C++
And here are some for inverting the mersenne twister:
http://www.randombit.net/bitbashing/2009/07/21/inverting_mt19937_tempering.html
http://b10l.com/reversing-the-mersenne-twister-rng-temper-function/
In general, no. It should be possible for most generators if you have the full array of numbers. If you don't have all of the numbers or know which numbers you have (do you have the 12th or the 300th?), you can't figure it out at all, because you wouldn't know where to stop.
You would have to know the details of the generator. Decoding a linear congruential generator is going to be different from doing so for a counter-based PRNG, which is going to be different from the Mersenne twister, which is going to be different with a Fibonacci generator. Plus you would probably need to know the parameters of the generator. If you had all of that AND the equation to generate a number is invertible, then it is possible. As to how, it really depends on the PRNG.
Use the language Janus a time-reversible language for doing reversible computing.
You could probably do something like create a program that does this (pseudo-code):
x = seed
x = my_Janus_prng(x)
x = reversible_modulus_op(x, N) + offset
Janus has the ability to give to you a program that takes the output number and whatever other data it needs to invert everything, and give you the program that ends with x = seed.
I don't know all the details about Janus or how you could do this, but just thought I would mention it.
Clearly, what you want to do is probably a better idea because if the RNG is not an injective function, then what should it map back to etc.
So you want to write a Janus program that outputs an array. The input to the Janus inverted program would then take an array (ideally).

When should I write my own random number algorithm instead of using a stock math function?

So I am taking a scripting test in Lua, and I am given this question:
Create an algorithm to generate a deck of cards, 1-52. Shuffle the deck of cards (do not use something like array.randomize() ). Then hand out 5 cards to two different players. Being that each card must be dealt to a different player at a time.
Typically I would do something like this to get a random number
local newDeck = {} --assume this array has all 52 cards in a playing deck
math.randomseed( os.time() )
local card = math.random(#newDeck)
...but it seems that the question is specifically asking that I do NOT use a stock math function.
(do not use something like array.randomize())
What would be the advantage to that? I can't imagine that the player of such a game would even notice a difference between random and pseudo random.
If only it were that simple. Most random number generators that are part of a language are linear congruential generators, meaning that the next term J, say, is related to the previous one I by
J = (aI + b) mod c
Where a, b, c are constants.
This means that it is possible to decipher the sequence from a single digit number of terms! (It's a set of simultaneous equations with bit of trickery to handle the modulus).
I'd say that an astute player is bound to notice the pseudo random nature of your sequence and may even game the system by unpicking your generator. You need to use a more sophisticated scheme. (Early attempts include Park-Miller and Bays-Durham; fairly well-known approaches).
I believe you are welcome to use the built in random number generator to get random numbers, but prohibited from using any built in array shufflers that may exist. How can you use a rng to have each card equally likely to be in each position?
you could just write something that draws a random card and puts it in the shuffled deck:
function shuf(tab)
local new = {}
for k=1,#tab do
new[#new+1]=table.remove(tab,math.random(#tab))
end
end
This approach makes sure you have no doubles.
I don't really think using a different RNG would matter that much unless you're doing cryptography, or something else that really matters.
Interpreting the question: just don't use a library function written for doing this. But there is a difference between a shuffler and a random number generator, since the latter can return double values while the former can't.

I'm looking for a good psuedo random number generator, that takes two inputs instead of one

I'm looking for a determenistic psuedo random generator that takes two inputs and always returns the same output. I'm looking for things like uniform distribution, unpredictable as possible, and doesn't repeat for a long long time. Ideally the function doesn't rely on previous values. The reason that is a problem is I'm generating terrain data for an extremely large procedurely generated world and can't afford to store previous values.
Any help is appreciated.
i think what you're looking for is perlin noise - it's a way of generating "random" values in 2d (typically) that look like terrain / clouds / etc.
note that this doesn't have much to do with cryptography etc, but a "real" random number source is probably not what you want for synthetic terrain (it looks too noisy/spikey).
there's a good article on perlin noise here.
the implementation of perlin noise does use a source of random numbers, but typically you can use whatever is present on your system (starting with a known seed if you want to reproduce it later).
Is the problem deciding on a PRNG algorithm to use or an algorithm that accepts 2 inputs?
If it's the former, why not use the built in random class - such as Random class in .NET - since it strives for uniform distribution and long cycles. Also, given the same seed it will generate the same sequence of numbers.
If it's the latter, what you can do is map the 2 inputs to a single ouput and use that as a seed to your random algorithm. You can define a simple hash function that takes a string and calculates an integer from it:
s[0] + s[1]^1 + s[2]^2 + ... s[n]^n = seed
Combination of two inputs (by concatenating each other, provided the inputs are binary integers) into one seed will do, for a PRNG, such as Mersenne Twister.

Random number generation

I need a random number generation algorithm that generates a random number for a specific input. But it will generate the same number every time it gets the same input. If this kind of algorithm available in the internet or i have to build one. If exists and any one knows that please let me know. (c, c++ , java, c# or any pseudo code will help much)
Thanks in advance.
You may want to look at the built in Java class Random. The description fits what you want.
Usually the standard implementation of random number generator depends on seed value.
You can use standard random with seed value set to some hash function of your input.
C# example:
string input = "Foo";
Random rnd = new Random(input.GetHashCode());
int random = rnd.Next();
I would use a hash function like SHA or MD5, this will generate the same output for a given input every time.
An example to generate a hash in java is here.
The Mersenne Twister algorithm is a good predictable random number generator. There are implementations in most languages.
How about..
public int getRandonNumber()
{
// decided by a roll of a dice. Can't get fairer than that!
return 4;
}
Or did you want a random number each time?
:-)
Some code like this should work for you:
MIN_VALUE + ((MAX_VALUE - MIN_VALUE +1) * RANDOM_INPUT / (MAX_VALUE + 1))
MIN_VALUE - Lower Bound
MAX_VALUE - Upper Bound
RANDOM_INPUT - Input Number
All pseudo-random number generators (which is what most RNGs on computers are) will generate the same sequence of numbers from a starting input, the seed. So you can use whatever RNG is available in your programming language of choice.
Given that you want one sample from a given seed, I'd steer clear of Mersenne Twister and other complex RNGs that have good statistical properties since you don't need it. You could use a simple LCG, or you could use a hash function like MD5. One problem with LCG is that often for a small seed the next value is always in the same region since the modulo doesn't apply, so if your input value is typically small I'd use MD5 for example.

Resources