Seed unique random numbers

Is there a way of using a rand-function in a way that it seeds the same random numbers every time the function is used? I'm looking fomr something like:

1
2
3
4
int * randfunction(hash maybe){
   //Fancy code...
   return // quasi random numbers, same each time function is used.
}


I'm testing an algorithm where I need a set of unique random numbers. So far I've only used hard coded numbers on small scale test runs. I'd like to do the up scaling, but haven't really figured out how to seed random numbers like I need to.

Any suggestions are welcome.

Thanks!
I think I solved your question, actually quite proud of myself because I've been trying to answer your question for the last 20 minutes using some beginner knowledge lol, it was mainly guessing :D
Anyway each function you call gives a different set of the same random numbers. Hope this helps :)

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
#include <iostream>
#include <cstdlib>
using namespace std;

class RandFunction{
public:
	void Random1(){
		srand(1);
	}
	void Random2(){
		srand(2);
	}
};

int main(){
	RandFunction RandObject;
	RandObject.Random1();
	for(int x = 1; x < 10; x++){
		cout << 1+rand()%6 << endl;
	}

	cout << endl;

	RandObject.Random2();
	for(int x = 1; x < 10; x++){
		cout << 1+rand()%6 << endl;
	}
}
Last edited on
Setting a new seed is an odd thing to do. Also, if you're setting a new seed from the time (quite a common thing to do), you would have to ensure at least 1 second has passed definitely every time a function was called.

I would suggest a better method would be to use the mersenne twister from <random>, which is a great header file with lots of useful random number generations. You can use just one generated twister to obtain all your unique random sets. Each set can be an array or vector or whatever that is filled from that twister each time.

Here is a link to the reference on here: http://www.cplusplus.com/reference/random/

You will need to be sure to be using an up to date compiler to have the <random> library available.
Alex, thanks but I have other ideas now.

Mats, I'll check it up, thanks!

It seems I have an version of Fisher Yates in my code stash. I think it will do the job.
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
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
#include <random>
#include <algorithm>
#include <vector>
#include <set>
#include <iostream>
#include <iomanip>

// initialize the rng with a seed
// for the same seed, will generate the same sequence of quasi random numbers
std::mt19937 initialize_twister( int seed )
{
    static constexpr std::size_t NDISCARD = 1024 ;

    std::minstd_rand lcg(seed) ;
    lcg.discard(NDISCARD) ;

    std::size_t seeds[ std::mt19937::state_size ] ;
    std::generate_n( seeds, std::mt19937::state_size, lcg ) ;

    std::seed_seq seed_sequence( std::begin(seeds), std::end(seeds) ) ;
    std::mt19937 twister { seed_sequence } ; // warm-up
    twister.discard(NDISCARD) ; // warm-up

    return twister ;
}

// generate n uniformly distributed, unique, random numbers with the rng
std::vector<int> generate_unique( std::mt19937& rng, std::size_t n, int minv, int maxv )
{
    std::uniform_int_distribution<int> distr( minv, maxv ) ;
    std::set<int> set ;
    while( set.size() < n ) set.insert( distr(rng) ) ;
    return { set.begin(), set.end() } ;
}

// generate a new quasi random permuatation of the numbers (fisher yates shuffle)
std::vector<int> shuffle( std::vector<int>& seq )
{
    static std::mt19937 rng = initialize_twister(1000) ;
    std::shuffle( std::begin(seq), std::end(seq), rng ) ;
    return seq ;
}

int main()
{
    constexpr int N = 2 ;
    int seeds[N] { 5678, 111111 };

    std::vector<std::mt19937> rngs ; // quasi rngs
    for( int s : seeds ) rngs.push_back( initialize_twister(s) ) ;

    std::cout << "---------------------------------------------\n" ;
    for( auto& twister : rngs ) // for each rng
    {
        // generate 10 quasi random numbers uniformly distributed in [0,9999]
        std::vector<int> seq = generate_unique( twister, 10, 0, 9999 ) ;

        // print three quasi random sequences of these numbers
        for( int i = 0 ; i < 3 ; ++i )
        {
            shuffle(seq) ;
            for( int v : seq ) std::cout << std::setw(5) << v ;
            std::cout << '\n' ;
        }
        std::cout << '\n' ;
    }
}

http://coliru.stacked-crooked.com/a/8d5e11180d04bd0b
Topic archived. No new replies allowed.