How to pick a random element from a vector filled with .txt file names C++

5.5k views Asked by At

I stored a long list of names from a .txt file into a vector called BunnyNames, and I am trying to find a way to randomly generate elements (names) from within said vector. So far all it's doing is printing the names consecutively from the .txt file instead of randomly like I want. Here is my code:

int main()

{
    using namespace std;

    string name;
    vector<string> BunnyNames;

    ifstream myfile("names.txt");

    if(!myfile)
    {
        cerr <<"Error opening output file"<< endl;
        system("pause");
        return -1;
    }
    while (getline(myfile, name))
    {
        BunnyNames.push_back(name);
    }

    srand (time(0));
    int randomIndex = rand() % BunnyNames.size();

    std::cout<<BunnyNames[randomIndex]<<std::endl;
    return 0;
}

I only want it to print one name at a time, but I want that one name to be random.

Here are the first few lines of the file:

Abracadabra
Ace
Akeeta
3

There are 3 answers

2
Saksham On

Considering that you want to randomly access vector elements, this might be because you are setting the seed inside the loop.

Try seeding it only one at the beginning and use rand() % BunnyNames.size() inside the loop as:

srand (time(0));
while(condition)
{
    int randomIndex = rand() % BunnyNames.size();
}

Another case might be that the loop is iterating fast enough that in successive iterations, the time doesn't change, thus generating same values.

0
Adam Schmidt On

Thank you for your help everyone. It turns out that it was in fact printing out random names, but I didn't catch it because the names still appeared to be going alphabetically. I didn't realize that it was skipping groups of names at a time, depending on how long it was before I re-ran the program (since srand (time(0)) is based off of time).

0
Benjamin Lindley On

The problem is, if you run the program repeatedly in close succession, you use the same, or very similar seeds (because the time doesn't change much). You need to devise a way to either generate a wildly different seed each run of the program, or create a random number generator which you can save the state of. For example, you could do this:

unsigned int seed = time(0);
std::ifstream fin("rand.txt");
if (fin)
{
    fin >> seed;
    fin.close();
}

srand(seed);
seed = rand();
unsigned int randomIndex = seed % BunnyNames.size();

std::ofstream fout("rand.txt");
fout << seed;

It saves the generated number from the previous run of the program into a file, then uses that value for the seed on the next run.