简体   繁体   中英

Should C++ std::uniform_real_distribution<double> only generate positive numbers?

I was trying to generate some random doubles in C++ (MSVC, though that isn't too important to me—I just didn't have another compiler to test) and I noticed that my quick program never generated negative numbers:

#include <iostream>
#include <random>
#include <ctime>

int main() {
    std::mt19937 generator(clock());
    std::uniform_real_distribution<double>
        rand_dbl(std::numeric_limits<double>::min(),
                 std::numeric_limits<double>::max());

    std::cout << "Double Limits: (" << std::numeric_limits<double>::min()
              << "," << std::numeric_limits<double>::max() << ")"
              << std::endl << std::endl;

    int total_neg = 0;
    for (int i=0; i<100; i++) {
        double d = rand_dbl(generator);
        if (d<0) total_neg++;
        std::cout << d << " ";
    }
    std::cout << std::endl << std::endl
              << "Total negative random double is: " << total_neg << std::endl;

    return 0;
}

No matter how many numbers I have it generate, it never generates a negative one. I understand why most of the numbers generated are in the 10 307 - 10 308 range (which isn't exactly what I wanted), but not why the numbers are always positive. I tried a few different generators (default, mt19937 , minstd_rand0 ) without any difference in this aspect.

Can anyone describe why this is the case?

You set it up that way with the limits that you provided. std::numeric_limits<double>::min() gives the smallest positive double, and you used that as the lower bound on the distribution.

std::numeric_limits<double>::min()

Will return DBL_MIN which is the smalles value closest to 0 a double can hold. If you want the largest negative value then you need to use

std::numeric_limits<double>::lowest()

Which will return -DBL_MAX which is the largest negative value a double can hold.

From cppreference :

For floating-point types with denormalization, min returns the minimum positive normalized value.

(emphasis mine)

So it's pretty normal you only get positive values.

Could you tell what is displayed by those lines?

std::cout << "Double Limits: (" << std::numeric_limits<double>::min()
          << "," << std::numeric_limits<double>::max() << ")"
          << std::endl << std::endl;

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM