Random Number from an Array

Hello there!
I wanna know if there is any posibility to get a random number from Array?
I want to get one random number from this Array:

const int array[5] = { 5, 10 , 123, 234, 2};

Can somebody give me some advice?


One way:
https://en.cppreference.com/w/cpp/numeric/random/uniform_int_distribution
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#include <random>
#include <iostream>
 
int main()
{
    std::random_device rd;  // Will be used to obtain a seed for the random number engine
    std::mt19937 gen(rd()); // Standard mersenne_twister_engine seeded with rd()
    std::uniform_int_distribution<> distrib(0, 4);

    const int array[5] = { 5, 10 , 123, 234, 2};
    
    //Use 'distrib' to transform the random unsigned int generated by gen into an int in [0, 4]
    int random_index = distrib(gen);
    std::cout << array[random_index] << '\n';
}


If random_device is not available,
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#include <iostream>
#include <chrono>
#include <random>

int main()
{
    unsigned seed = std::chrono::system_clock::now().time_since_epoch().count();
    std::mt19937 gen(seed);
    std::uniform_int_distribution<> dist(0, 4);

    const int array[5] = { 5, 10 , 123, 234, 2};
    
    int random_index = dist(gen);
    std::cout << array[random_index] << '\n';
}
Last edited on
WOW!
Thank you for this quick response!
I'll try this out.


Although it's probably not important in this case, it should be mentioned that seeding 19937 bits of state with a single rd() call is not best practice. :) Although IIRC, properly seeding the mt is problematic.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
#include <iostream>
#include <random>
#include <type_traits>
#include <algorithm>

template<typename T, size_t N>
void print(T(&a)[N]) {
    for (size_t i = 0; i < N; ++i) std::cout << a[i] << ' ';
    std::cout << '\n';
}

int main() {
    using std::cout;

    std::random_device rd;
    std::seed_seq seeder{rd(), rd(), rd(), rd(), rd(), rd(), rd(), rd(),
                         rd(), rd(), rd(), rd(), rd(), rd(), rd(), rd()};
    auto rnd{std::mt19937(seeder)};
    rnd.discard(rd() % 256);

    int a[] { 5, 10, 15, 20, 25, 30 };
    int size = std::extent_v<decltype(a)>; // pre-C++17: extent<...>::value
    std::uniform_int_distribution<> dist(0, size - 1);

    // Choosing randomly from the entire array each time results
    // in repeating values.
    for (int i = 0; i < 20; ++i) cout << a[dist(rnd)] << ' ';
    cout << '\n';

    // shuffling gives you the numbers in a random order without repeats
    for (int i = 0; i < 5; ++i) {
        std::shuffle(a, a + size, rnd);
        print(a);
    }
}

Last edited on
Yeah I know, you are correct, only seeding mt19937 with one unsigned int highly diminishes the amount of possible states. Although I'd say it's "good enough", and I would use other libraries if I was actually doing something for cryptographic purposes.
That's so bad. The most direct route to use a library should not lead you to use it poorly. Hell, normally it should not even be necessary to explicitly seed the PRNG. The default constructor should try to provide the best source of entropy.
Last edited on
Indeed.

Alas, even the seed_seq might be problematic: https://www.pcg-random.org/posts/cpp-seeding-surprises.html
Alas, even the seed_seq might be problematic

That's what I meant by "properly seeding the mt is problematic".
It's apparently broken.
Topic archived. No new replies allowed.