On Mon, Nov 6, 2017 at 11:10 AM, Steven Watanabe via Boost < boost@lists.boost.org> wrote:
uniform_int_distribution is not excess weight. You could use independent_bits_engine instead, but if you accept an arbitrary random engine, then you need some way to convert its output into the correct range. Not all engines produce uniformly distributed 32-bit output.
Filling a uuid with random does not require integers. In this case as long as the UniformRandomNumberGenerator produces at least one byte from operator() then it is sufficient to fill the contents of a uuid randomly. If it returns more than that, it will be more efficient. I have a macro that makes a header-only random_device type and it is used as follows: namespace detail { BOOST_TTI_HAS_MEMBER_FUNCTION(seed) } template<class MaybePseudoRandomNumberGenerator> typename boost::enable_if<detail::has_member_function_seed<MaybePseudoRandomNumberGenerator, void> >::type seed(MaybePseudoRandomNumberGenerator& rng) { BOOST_UUID_DETAIL_MAKE_RANDOM_DEVICE_TYPE(unsigned int, seed_random_device); using boost::function_input_iterator; using boost::make_function_input_iterator; boost::infinite inf; seed_random_device egen; function_input_iterator<seed_random_device, boost::infinite> beg = make_function_input_iterator(egen, inf); function_input_iterator<seed_random_device, boost::infinite> end = make_function_input_iterator(egen, inf); rng.seed(beg, end); } internally this is used to obtain seeding for PRNGs. One can use this in various ways, and it is not limited to the unsigned int size, for example: BOOST_UUID_DETAIL_MAKE_RANDOM_DEVICE_TYPE(uuid, uuid_random_device); typedef basic_random_generator<uuid_random_device> random_generator; Now the random_generator obtains 16 bytes of entropy in a single call, rather than making 4 calls for 4 bytes each. This technique might be applicable to the existing PRNGs in Boost.Random with a header-only random_device implementation. For example it may be possible to have the mersenne twister make one entropy call for 623 bytes instead of making 156 calls for 4 bytes at a time. I haven't looked in detail at the way it seeds itself, however: struct mersenne_entropy_pod { uint8_t entropy[623]; } BOOST_UUID_DETAIL_MAKE_RANDOM_DEVICE_TYPE(mersenne_entropy_pod, mersenne_seed_random_device); Then mersenne_twister could call mersenne_seed_random_device()() to get 623 bytes of entropy in a single system call. - Jim