0

I am using Windows/MinGW. I have the following code to generate random ranges whenever I need:

random_device rd;
mt19937 eng(rd());

int get_random_int(int from, int to){
    uniform_int_distribution<int> dist(from, to);
    return dist(rd);
}

How do I feed the engine with a random seed like the current time or whatever? (I've tried to replace rd with time, but it's not possible). In my game, the enemies spawn in random positions in all directions and start moving towards you. It happens that, every time I start the game, they spawn in the same places (And that's exactly the opposite of what I want, since they're going to feel predictable).

EDIT (The procedure that generates the enemies):

void generate_enemies(int q, int speed) {
    for (int i = 0; i < q; i++) {
        Actor a;
        a.facing = get_random_int(0, 3);
        a.speed = speed;
        if (a.facing == UP) {
            a.x = get_random_int(0, SCREEN_WIDTH);
            a.y = -get_random_int(SCREEN_HEIGHT, SCREEN_HEIGHT + get_random_int(0, ENEMY_DISTANCE_FACTOR * get_random_int(0, ENEMY_DISTANCE_MULTIPLICATIVE_FACTOR)));
        } else if (a.facing == DOWN) {
            a.x = get_random_int(0, SCREEN_WIDTH);
            a.y = get_random_int(SCREEN_HEIGHT, SCREEN_HEIGHT + get_random_int(0, ENEMY_DISTANCE_FACTOR * get_random_int(0, ENEMY_DISTANCE_MULTIPLICATIVE_FACTOR)));
        } else if (a.facing == LEFT) {
            a.x = -get_random_int(SCREEN_WIDTH, SCREEN_WIDTH + get_random_int(0, ENEMY_DISTANCE_FACTOR * get_random_int(0, ENEMY_DISTANCE_MULTIPLICATIVE_FACTOR)));
            a.y = get_random_int(0, SCREEN_HEIGHT);
        } else if (a.facing == RIGHT) {
            a.x = get_random_int(SCREEN_WIDTH, SCREEN_WIDTH + get_random_int(0, ENEMY_DISTANCE_FACTOR * get_random_int(0, ENEMY_DISTANCE_MULTIPLICATIVE_FACTOR)));
            a.y = get_random_int(0, SCREEN_HEIGHT);
        }
        enemies.push_back(a);
    }
}
vsoftco
  • 55,410
  • 12
  • 139
  • 252
Ericson Willians
  • 7,606
  • 11
  • 63
  • 114
  • `random_device` should be pretty darn good (on linux is based on hardware effects), better than using `time(0)` for sure. Do your objects spawn in exactly the same positions each new run? – vsoftco May 16 '15 at 03:08
  • Always in the same place, always the same values, and it was supposed to be a "random seed". It's really curious. – Ericson Willians May 16 '15 at 03:10
  • I'm just running your code http://ideone.com/aBtF0S, and it produces different values at each run, even for super fast consecutive runs. What compiler/system are you using? Do you happen to pass your RNG by value to some function, so it copies its state? (even though you should still get different results on different runs) – vsoftco May 16 '15 at 03:13
  • I'm not on Linux, I'm on Windows 7 (And I'm using the latest version of MinGW). – Ericson Willians May 16 '15 at 03:16
  • I'll edit the post and add the procedure. – Ericson Willians May 16 '15 at 03:18
  • Just out of curiosity, can you test the code I posted on ideone? Does it give you different results at each run? – vsoftco May 16 '15 at 03:24
  • I've just tested it and it produces the same result at each run. I wonder if it has to do with the platform... – Ericson Willians May 16 '15 at 03:28
  • 2
    MinGW's `random_device` is broken. Use `boost::random_device` instead. – T.C. May 16 '15 at 03:33
  • 1
    @RederickDeathwill then it's an issue with the platform/implementation. http://stackoverflow.com/q/18880654/3093378 – vsoftco May 16 '15 at 03:34
  • 1
    /dev/urandom will generate "reliable" random numbers and hence no need to set the seed yourself. std::random_device by default uses /dev/urandom and hence it should meet your requirement. – Nipun Talukdar May 16 '15 at 03:34
  • 1
    @NipunTalukdar the OP problem is that the implementation itself is broken (his code is OK) – vsoftco May 16 '15 at 03:36
  • 1
    @T.C. I don't think this is a duplicate. The other question is asking *why* but is not seeking a solution. This question is asking for a solution. – Galik May 16 '15 at 03:51
  • To emulate a random device you can use time and `std::seed_seq` [doc](http://en.cppreference.com/w/cpp/numeric/random/seed_seq). This way the time will be converted into a high entropy seed for the mersenne twister. The sequence can also be initialized with only one number. Also you should use `dist(eng)` in `get_random_int` to use the mersenne twister instead of the random device. – Max Linke May 16 '15 at 17:25

0 Answers0