I need to generate random Boolean values on a performance-critical path.
The code which I wrote for this is
std::random_device rd;
std::uniform_int_distribution<> randomizer(0, 1);
const int val randomizer(std::mt19937(rd()));
const bool isDirectionChanged = static_cast<bool>(val);
But do not think that this is the best way to do this as I do not like doing static_cast<bool>
.
On the web I have found a few more solutions
1. std::bernoulli_distribution
2. bool randbool = rand() & 1;
Remember to call srand()
at the beginning.
If performance is your only criterion, then the answer is:
Unfortunately, the entropy of this random number is zero, but the performance is quite fast.
Since I suspect that this random number generator is not very useful to you, you will need to quantify how random you want your booleans to be. How about a cycle length of 2048? One million? 2^19937-1? Until the end of the universe?
I suspect that, since you explicitly stated that performance is your utmost concern, then a good old fashioned linear congruential generator might be "good enough". Based on this article, I'm guessing that this generator's period is around 32*((2^31)-5), or about 68 trillion iterations. If that's not "good enough", you can drop in any C++11 compatible generator you like instead of minstd_rand.
For extra credit, and a small performance hit, modify the below code to use the biased coin algorithm to remove bias in the generator.
Some quick benchmarks (code):
For those who want ready-to-use code, I present
XorShift128PlusBitShifterPseudoRandomBooleanGenerator
, a tweaked version ofRandomizerXorshiftPlus
from the above link. On my machine, it is about as fast as @SergeRogatch's solution, but consistently about 10-20% faster when the loop count is high (≳100,000), and up to ~30% slower with smaller loop counts.Apparently I have to add another answer. Just figured out that starting with Ivy Bridge architecture Intel added RdRand CPU instruction and AMD added it later in June 2015. So if you are targeting a processor that is new enough and don't mind using (inline) assembly, the fastest way to generate random
bool
s should be in callingRdRand
CPU instruction to get a 64-bit random number as described here (scroll to approximately the middle of the page for code examples) (at that link there is also a code example for checking the current CPU for support of RdRand instruction, and see also the Wikipedia for an explanation of how to do this with CPUID instruction), and then use the bits of that number for booleans as described in my Xorshit+ based answer.iI think that best way is an using of precalculated random array:
It using to fill some array dst[size]:
Of course you can initialize pre-calculated array with using of another random function.
if performance is important, perhaps it's a good idea to generate a 32 bit random number and use each separate bit of it, something like this:
this way the generation only impacts every 32th call
For the purpose of performance, at a price of less "randomness" than e.g.
std::mt19937_64
, you can use Xorshift+ to generate 64-bit numbers and then use the bits of those numbers as pseudo-random booleans.Quoting the Wikipedia:
Details: http://xorshift.di.unimi.it/ . There is a comparison table in the middle of the page, showing that
mt19937_64
is 2 times slower and is systematic.Below is sample code (the real code should wrap it in a class):