Reputation: 2562
I have some letters in an array, only 8 of them, starting at A and ending at H. Using a typical random number generator, I have found that A and H are very rarely generated. How can I make this more inclusive for these two bounds?
var allowedLetters = ["A","B","C","D","E","F","G","H"];
var i = Math.round(Math.random() * (allowedLetters.length - 1));
var letter = allowedLetters[i];
console.log(letter)
Upvotes: 1
Views: 487
Reputation: 24581
var allowedLetters = ["A","B","C","D","E","F","G","H"];
var calledTimes = [0,0,0,0,0,0,0,0];
var i = 0;
while (i++ < 100000) calledTimes[Math.round(Math.random() * (allowedLetters.length - 1))]++;
console.log(calledTimes);
This happens because of Math.round
specifics. Use Math.floor
instead:
var allowedLetters = ["A","B","C","D","E","F","G","H"];
var calledTimes = [0,0,0,0,0,0,0,0];
var i = 0;
while (i++ < 100000) calledTimes[Math.floor(Math.random() * allowedLetters.length)]++;
console.log(calledTimes);
Upvotes: 0
Reputation: 386756
round
is is wrong, because only half of the slot of the random values goes to the lower index and half of the slot goes to the upper index.
var values = ["A", "B", "C", "D", "E", "F", "G", "H"],
index,
count = {},
i = 1e6;
while (i--) {
index = Math.round(Math.random() * (values.length - 1));
count[values[index]] = (count[values[index]] || 0) + 1;
}
console.log(count);
You could use Math.floor
with the full length of the array as factor.
var values = ["A", "B", "C", "D", "E", "F", "G", "H"],
index,
count = {},
i = 1e6;
while (i--) {
index = Math.floor(Math.random() * values.length);
count[values[index]] = (count[values[index]] || 0) + 1;
}
console.log(count);
Upvotes: 1
Reputation: 138477
var i = Math.round(Math.random() * (allowedLetters.length - 1));
Cause the first and the last element got a range of 0.5
, all the others got 1
. Might do this instead:
var i = Math.floor(Math.random() * allowedLetters.length);
Were all elements get the same distribution.
Upvotes: 2