How do I get a cryptographically strong number in the range [0,1)?
I am trying to create a function that will return a random decimal number between 0 (inclusive) and 1 (excluding) using a function Window.crypto.getRandomValues()
. Currently my code looks like this:
var rand = function(){
var ra = window.crypto.getRandomValues(new Uint32Array(1))[0];
function dec(n,m){
return (n>=0&&n<=1)?n:dec(n/m,m);
}
return dec(ra,8);
}
My problem is that this is unevenly distributed; it tends to be between .2 and .7 and rarely falls under 0.2 or more than .7. Is there a better way to use a method .getRandomValues()
to get a number like the function number Math.random()
?
I am not using the method .random()
because I want to have safe numbers for what I am trying to accomplish.
Why not simplify things
function cryptoRandom() {
return window.crypto.getRandomValues(new Uint32Array(1))[0] / 0x100000000;
}
What's going on here?
- Suppose it
window.crypto.getRandomValues
will give us some really random bits - Request 32 bits (unsigned integer
i
) min
Ium valuei
is0x00000000
(or0
)max
Imum valuei
is0xFFFFFFFF
(or4294967295
)- Convert these points to the desired range;
(i - min) / (max + 1)