-1

I'm building a simulation of a reality game and I need to randomly pick the indexes of the players which will take part in every round of a competition. The problem is, that while on the first round the indexes are sometimes the same for both teams and sometimes not, on the second and third round there are always the same indexes in both teams. Could anyone shed some light on this?

Code follows:

#include <iostream>

using namespace std;

int ArraySearch(int* a, int num);

int compete()
{
    int round = 0; //current round
    int temp = 0;  //(temporary) random player index
    int Team1Players[5];  //player indexes of team 1
    int Team2Players[5];  //indexes of 2

    round++; //start from the 1st round

    while (round < 4)  //competition lasts for 3 rounds
    {
        srand(time(NULL));
        cout << "This is Round " << round << endl;  //DEBUG MSG

        cout << "Team 1 Players: ";  //DEBUG MSG
        for (int i = 0; i < 5; i++)
        {
            do     //change the chosen number when it already exists
            {
                temp = rand() % 11;
                Team1Players[i] = temp;
                //cout << "Grabbed a random number for team 1: " << Team1Players[i] << endl; //DEBUG MSG
            }
            while (ArraySearch(Team1Players, temp) == 1);
            cout << Team1Players[i] << " "; //DEBUG MSG
        }
        cout << endl;

        cout << "Team 2 Players: ";
        for (int i = 0; i < 5; i++)
        {
            do //same as above for team 2
            {
                temp = rand() % 11;
                Team2Players[i] = temp;
                //cout << "Grabbed a random number for team 2: " << Team2Players[i] << endl; //DEBUG MSG

            }
            while (ArraySearch(Team2Players, temp) == 1);
            cout << Team2Players[i] << " "; //DEBUG MSG
        }
        cout << endl;
        round++;
    }
}

int ArraySearch(int* a, int num)  //returns 1 when a number exists more than once, 0 when it does not exist or is unique
{
    int occurrences = 0;
    for (int i = 0; i < 5; i++)
    {
        if (a[i] == num)
        {
            occurrences += 1;
        }
    }
    if (occurrences > 1)
    {
        return 1;
    }
    return 0;
}

Many thanks in advance.

Christophe
  • 68,716
  • 7
  • 72
  • 138
  • `srand(time(NULL));` belongs at the beginning of main and should only be called once. I assume your rounds happen in the same second, and you've told the random generator to start with the same number every time. – Retired Ninja May 04 '18 at 22:35

2 Answers2

2

You should seed rand once for the entire program. This is reason you're seeing the issue. Move this line to be at the top of main:

srand(time(NULL));

But wait, is rand even the right choice here? It turns out rand is actually usually not a good idea (see this great talk for more). Instead, like this question, you should be using <random>:

#include <random>

std::random_device rseed;
std::mt19937 rgen(rseed()); // mersenne_twister
std::uniform_int_distribution<int> idist(0,10); // [0,100]

int compete() {
    ...
    temp = idist(rgen);
scohe001
  • 15,110
  • 2
  • 31
  • 51
0

The random numbers return by rand() are not really random. They are pseudo-random, in the sense that they belong to a sequence that seems to be random and cannot be easily guessed. The start of the sequence is seeded with srand().

Problem

The problem that you experience is because you seed the random numbers in every iteration of your loop, based on the current time():

   srand(time(NULL));

The accuracy of the timing is implementation dependent, but most implementations are at the precision of the second. Unfortunately, you loop can be fast enough that the timestamp is the same, so that you'll get again the same sequence of random numbers, again and again until you reach the next second.

Solution

Set the seed only once in your application, so before entering in the loop.

Christophe
  • 68,716
  • 7
  • 72
  • 138