Thread: Random integers (numbers) - help

  1. #1
    Registered User danielcplusplus's Avatar
    Join Date
    Aug 2014
    Location
    earth
    Posts
    14

    Random integers (numbers) - help

    Hey all, I'm trying to make a C++ program that generate 6 random numbers ( from 100,000 to 999,999 ), okay, so I wrote a few lines..

    Code:
    srand(time(0));
    for (int i = 0; i < 5; i++)
    {
        std::cout << 100000 + (rand() % 999999) << std::endl;
    }

    The problem is, that it generates numbers like this:
    117,207
    123,303
    131,083
    ... etc etc..
    They're all starts with 100K, i want them to be an actual random..
    Already looked on google, didn't found what i was looking for.. so, anyone ?

    Thanks ^^

  2. #2
    C++まいる!Cをこわせ!
    Join Date
    Oct 2007
    Location
    Inside my computer
    Posts
    24,654
    You may want to use C++11's random number facilities: Pseudo-random number generation - cppreference.com
    To be honest, it's a little more complicated than it needs to be, but it gets the job done.

    Basically, what you do is create an engine (an engine creates random numbers), initialize it with a seed, and then create a distribution (takes numbers outputted from an engine and forces them into a statistical distribution, such as a uniform range) and then just repeatedly call the distribution to get your random numbers:

    std::random_device rnd; // This is a random engine which will produce our seed.
    std::default_random_engine engine(rnd()); // Create our random engine and initialize it with a unique seed.
    std::uniform_int_distribution<int> dist(100000, 999999); // Create our distribution which will produce our random numbers. The parameters specify the range.
    for (int i = 0; i < 5; i++)
    std::cout << dist(engine); // Generate our random numbers by calling the distribution. It wants an engine from where to get its random numbers, so that's where our engine comes in.
    Last edited by Elysia; 10-17-2014 at 07:11 AM. Reason: Fix typo
    Quote Originally Posted by Adak View Post
    io.h certainly IS included in some modern compilers. It is no longer part of the standard for C, but it is nevertheless, included in the very latest Pelles C versions.
    Quote Originally Posted by Salem View Post
    You mean it's included as a crutch to help ancient programmers limp along without them having to relearn too much.

    Outside of your DOS world, your header file is meaningless.

  3. #3
    Registered User danielcplusplus's Avatar
    Join Date
    Aug 2014
    Location
    earth
    Posts
    14
    AWESOME thanks.

  4. #4
    Lurking whiteflags's Avatar
    Join Date
    Apr 2006
    Location
    United States
    Posts
    9,612
    Well I hesitate to talk about making the values from a PRNG "more random" because I don't trust my subjective point of view to be a good judge of randomness.
    I guess you just want a sample set of numbers whose members differ by a great order of magnitude. In that case, simply reject numbers from rand() (or your choice of RNG) that are too small in difference for your liking from some previous result.

    I did something not too complicated:
    Code:
    #include <ctime>
    #include <cstdlib>
    #include <iostream>
    #include <cmath>
    
    int pickFromRange(int min, int max)
    {
       return min + std::rand() % (max - min);
    }
    
    int main()
    {
       std::srand(static_cast<unsigned long>(time(0)));
      
       int previous, current;
       current = pickFromRange(100000, 999999);
       for (int loop = 0; loop < 5; loop++) {
          std::cout<<current<<endl;
          do {
             previous = current;
             current = pickFromRange(100000, 999999);
          } while (std::abs(current - previous) < 100000);
       }
    
    }
    While results can vary from run to run, I got this back:
    943165
    455593
    210764
    500128
    870009
    which looks pretty random.

  5. #5
    C++まいる!Cをこわせ!
    Join Date
    Oct 2007
    Location
    Inside my computer
    Posts
    24,654
    This, as we know, introduces bias, and we also know that it can generate pretty poor results depending on the implementation of rand(). We don't even know how long before the numbers start to loop, especially when you do things like this!
    When we have these C++11 facilities which guarantee specific properties, why wouldn't we use them? Plus it's less code.
    Quote Originally Posted by Adak View Post
    io.h certainly IS included in some modern compilers. It is no longer part of the standard for C, but it is nevertheless, included in the very latest Pelles C versions.
    Quote Originally Posted by Salem View Post
    You mean it's included as a crutch to help ancient programmers limp along without them having to relearn too much.

    Outside of your DOS world, your header file is meaningless.

  6. #6
    Lurking whiteflags's Avatar
    Join Date
    Apr 2006
    Location
    United States
    Posts
    9,612
    I frankly do not understand your criticism. Even if I wrote the example using C++11 features, I would still have said the same things about the problem.

    I believe any PRNG can give you results like this: 117,207; 123,303; 131,083; that don't differ a great degree in magnitude. I agree, humans are poor judges of randomness... but if you just want a swathe of generated numbers that differ greatly in magnitude, you have to enter selection bias.

  7. #7
    C++まいる!Cをこわせ!
    Join Date
    Oct 2007
    Location
    Inside my computer
    Posts
    24,654
    I do understand some of your criticism. To me, it seems the OP was worried about the random numbers not being very random at all (very close to each other), and the numbers the OP mentioned seemed pretty typical of a poor std::rand() implementation. That's why I suggested the C++11 facilities. These guarantee much stronger randomness and even guarantee a statistical distribution, which cannot be said for std::rand, and randomless is precisely what the OP wanted. That is why I opposed your solution because it introduces bias.

    But I agree that if we try to ensure that each generated number vary greatly in magnitude, then no matter what you do, you will enter selection bias as you say. But the criticism from me is that even so, we can a much better job thanks to C++11's random facilities. Even if we destroy the statistical distribution, we can still guarantee that we have quality generated random numbers and a large set of unique numbers before we loop around again. You cannot guarantee this with std::rand.
    Quote Originally Posted by Adak View Post
    io.h certainly IS included in some modern compilers. It is no longer part of the standard for C, but it is nevertheless, included in the very latest Pelles C versions.
    Quote Originally Posted by Salem View Post
    You mean it's included as a crutch to help ancient programmers limp along without them having to relearn too much.

    Outside of your DOS world, your header file is meaningless.

  8. #8
    Lurking whiteflags's Avatar
    Join Date
    Apr 2006
    Location
    United States
    Posts
    9,612
    I'm sorry I wrote code with rand().

    I'll just stop doing that I guess, no matter how trivial the code is.

  9. #9
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Quote Originally Posted by whiteflags
    I'm sorry I wrote code with rand().

    I'll just stop doing that I guess, no matter how trivial the code is.
    Dunno, it looks more trivial with the new random number facilities:
    Code:
    #include <random>
    #include <ctime>
    #include <iostream>
    
    int main()
    {
        std::mt19937 prng(static_cast<std::mt19937::result_type>(std::time(nullptr)));
        std::uniform_int_distribution<int> random(100000, 999999);
        for (int loop = 0; loop < 5; loop++) {
            std::cout << random(prng) << std::endl;
        }
    }
    Except that uh, it needs to be explained to the novice that the first line in main creates a pseudo-random number generator seeded based on current time, the second line creates a way to obtain the numbers within the given closed range with a uniform distribution (assuming that the PRNG has a uniform distribution), and then random(prng) connects the two to generate a pseudo-random number within the given range with a uniform distribution.

    Oh, then if we change the cast to result_type to use Prelude's idea of hashing the bytes of the time_t obtained as described in using rand(), I guess it becomes a little less trivial.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. arrays of random integers & time
    By meeloff in forum C++ Programming
    Replies: 3
    Last Post: 12-07-2004, 04:35 PM
  2. Replies: 4
    Last Post: 11-16-2004, 07:29 AM
  3. Writing a set of random integers to a file
    By RazielX in forum C Programming
    Replies: 19
    Last Post: 09-17-2004, 07:00 PM
  4. Replies: 4
    Last Post: 03-03-2003, 03:52 PM
  5. random integers
    By Unregistered in forum C Programming
    Replies: 2
    Last Post: 05-10-2002, 07:55 PM

Tags for this Thread