0

I was trying to generate some random numbers using rand() but I checked RAND_MAX first as I want to make some large numbers. In Windows 10 printf("%x",RAND_MAX); gives 0x7fff while on linux 18.04 printf("%x",RAND_MAX); gives 0x7ffffff Why the maximum range changes while I am using the same compiler GCC with same libraries on the same machine ? Is there is a way that I configure my IDE (code blocks) or compiler on Windows to get the same size as it on linux?

Hussien Mostafa
  • 159
  • 2
  • 18
  • 1
    `rand()` on many platforms is barely random at all. If you need really random libraries you need to use a proper random number library. – tadman Apr 15 '19 at 22:35
  • 1
    What _compiler_ and _version_ are you using under Windows. – chux - Reinstate Monica Apr 15 '19 at 22:38
  • 1
    `RAND_MAX` is guaranteed to be at least 32767. You can rely on at least 15-bits on all machines. Repeatedly call `rand()` until you accumulate the required number of bits. Also see the [`rand(3)` man page](http://man7.org/linux/man-pages/man3/rand.3.html) and [`RAND_MAX`](https://en.cppreference.com/w/cpp/numeric/random/RAND_MAX) docs. You might also be interested in [Understanding the algorithm of Visual C++'s rand() function](https://stackoverflow.com/q/6793065/608639) – jww Apr 15 '19 at 23:43
  • Thanks all of you guys – Hussien Mostafa May 31 '19 at 20:55

1 Answers1

2

It's not the same libraries. Linux is providing rand via a common libc (typically glibc) used by most Linux programs; Windows provides a different "common" C runtime, and many compilers and tools bundle their own version.

glibc is pretty Linux specific; you could always write your own srand/rand/RAND_MAX replacement library that follows the Linux conventions, but you can't just use Linux's unmodified.

If you want portable code, I'd suggest switching to C++ and using the C++11 <random> API, which has well-defined, portable semantics. rand is a terrible PRNG, and working to make it portable does nothing to fix the awfulness.

ShadowRanger
  • 143,180
  • 12
  • 188
  • 271
  • 1
    "Writing your own random number generator" is usually a bad plan. As you point out C++ has a fantastic suite of random number generation tools and is way more than a single person could ever hope to implement on their own without serious commitment and peer review. – tadman Apr 15 '19 at 22:35
  • 2
    @tadman: Well, in this particular case you can mostly just copy the implementation `glibc` uses. But I'm not really recommending it; the C++ `random` library is probably a better bet for portability. – ShadowRanger Apr 15 '19 at 22:37
  • 1
    "Windows provides a different "common" C runtime" --> not so sure the OS is providing the `rand()`. I suspect OP is not using `gcc` on Windows as reported. – chux - Reinstate Monica Apr 15 '19 at 22:37
  • 1
    @CacahueteFrito Or the Windows equivalent. That's where having a library, even the C++ Standard Library, helps. – tadman Apr 15 '19 at 22:52
  • 1
    *"`rand` is a terrible PRNG..."* - It depends on what it is being used for. `rand` is great for simulations because you get a number quickly from a uniform distribution. – jww Apr 15 '19 at 23:48
  • 2
    @CacahueteFrito: Did you mean `/dev/random`? Because that's not usually the best option (`/dev/urandom` is almost always what you want; the "extra security" of `/dev/random` is usually an illusion, and comes at the cost of triggering blocking operation), and it's not portable; the closest Windows equivalent is `CryptGenRandom`. – ShadowRanger Apr 16 '19 at 00:06
  • 1
    @jww: You can get quick random numbers without relying on a non-portable, often broken API. `rand` frequently has distribution issues, the minimum `RAND_MAX` is so low that you can't count on it being able to produce values of any magnitude, and getting an actual uniform distribution is surprisingly difficult to get right (if you need a value in the range `[0, n)`, `rand() % n` is frequently biased, especially on systems like Windows with low `RAND_MAX` values). The C++ PRNGs offer guaranteed implementations, safe distributions, etc. – ShadowRanger Apr 16 '19 at 00:10
  • 2
    *"`/dev/urandom` is almost always what you want"* - `/dev/urandom` is recommended; `/dev/random` is not. From Theodore Ts'o on the [kernel crypto](https://lkml.org/lkml/2017/7/20/993) mailing list: *"Practically no one uses /dev/random. It's essentially a deprecated interface; the primary interfaces that have been recommended for well over a decade is /dev/urandom, and now, getrandom(2)."* – jww Apr 16 '19 at 00:11
  • 1
    @ShadowRanger Yes I meant it. Thank you both for pointing out that it is deprecated. – alx - recommends codidact Apr 16 '19 at 12:25
  • Thanks all of you guys – Hussien Mostafa May 31 '19 at 20:56