Class Object question (C++)

Started by
2 comments, last by Steedie 17 years, 2 months ago
Hey guys, Been at work all day now so my mind just cant seem to work out the most simple (I think?) of tasks Basically, I'm trying to make it so that each time I create an object, certain variables (that are created by the rand function) are different each time an instance of that object is created I'm going to post the only bits I think that should matter, if anymore is needed please say and I'll post it asap. But basically, heres the constructor where these variables that I want to be different each time are declared and defined: agent::agent() { srand(time(NULL)); float colR = (float)((rand() % 10) + 1) * 0.1; float colG = (float)((rand() % 10) + 1) * 0.1; float colB = (float)((rand() % 10) + 1) * 0.1; float posX = (float)(rand() % 18) + 1; float posY = (float)(rand() % 18) + 1; index = (rand() % NUM_TARGETS) + 1; setPos(posX, posY, 0.0f); setVel(0.0f, 0.0f, 0.0f); setCol(colR, colG, colB); } As you can see its a pretty bodged way of creating those variables but its just while I work out how to fix this, which isnt going well with me being so tired lol. Its all of the variables using rand that I want to be different. Secondly, this is where I create the instances. gameWorld::gameWorld() { for(int i = 0; i < NUM_AGENTS; i++) { agent *newAgent = new agent; pAgent.push_back(newAgent); } } As you can see I'm just sticking them into a vector array. So yeah, basically at the moment, when I run the program, it creates 3 objects on screen at once like it should. But these objects all have the same colour properties and start in the same position, so only looks like I have one. Is there anyway, and I know there is as I've done something similar before, of making it so each time I create an object of this class, the properties of each are different. This is probably badly explained but explaining things has never been my strong point :( But if anyone can work out what Im getting at and fix it, you are my new best friend hehe Many thanks in advance
Advertisement
Your problem is that you call srand() every time. When you call srand() with the same seed, you'll get the same sequence of values from rand(). When you call time(NULL) multiple times quickly, you'll get the same value (not enough time has passed for time(NULL) to return a larger value). Thus, when you call srand(time(NULL)) multiple times quickly, you'll be generating the same seed over and over. The general idea is to only call srand() once, at the very beginning of your project.

I'd recommend, though, looking at the Boost Random Number Library. Using that, you could make your object take a random number generator in its constructor, and then use that to create random numbers (using whatever distributions your object needed). You could then create a single generator at the beginning of your program, seed it once, and then pass it to each of your objects as you construct them. This will have the added benefit of being safe from other libraries or pieces of code needing to reseed, since they'll merely be using another instance of a random number generator, or will still be using the old srand()/rand() pair.
"We should have a great fewer disputes in the world if words were taken for what they are, the signs of our ideas only, and not for things themselves." - John Locke
Quote:Original post by Steedie
agent::agent(){	srand(time(NULL));	float colR = (float)((rand() % 10) + 1) * 0.1;	float colG = (float)((rand() % 10) + 1) * 0.1;	float colB = (float)((rand() % 10) + 1) * 0.1;	float posX = (float)(rand() % 18) + 1;	float posY = (float)(rand() % 18) + 1;	index = (rand() % NUM_TARGETS) + 1;	setPos(posX, posY, 0.0f);	setVel(0.0f, 0.0f, 0.0f);	setCol(colR, colG, colB);}

it creates 3 objects on screen at once like it should. But these objects all have the same colour properties and start in the same position, so only looks like I have one.

You need to check out what exactly srand does. For most applications, it should only be called once, somewhere near the start of things. It tells the inner workings where to start generating numbers. So, what happens if you tell it "5", make some random numbers, then tell it "5" again? This basically resets the function, and it'll start over again at "5", making the same random numbers. Since your three objects are made within a second of each other (computers are fast, these days), they all reseed the rand( ) function with the same value, and wind up with the same values for their properties.

Here's the code as it should be, with srand( ) taken out of the constructor:
agent::agent(){float colR = (float)((rand() % 10) + 1) * 0.1;float colG = (float)((rand() % 10) + 1) * 0.1;float colB = (float)((rand() % 10) + 1) * 0.1;float posX = (float)(rand() % 18) + 1;float posY = (float)(rand() % 18) + 1;index = (rand() % NUM_TARGETS) + 1;setPos(posX, posY, 0.0f);setVel(0.0f, 0.0f, 0.0f);setCol(colR, colG, colB);}gameWorld::gameWorld(){srand(time(NULL));for(int i = 0; i < NUM_AGENTS; i++){agent *newAgent = new agent;pAgent.push_back(newAgent);}}

Ideally, srand(time(NULL)); should go as close to the beginning of main as possible.

Oh, and there are times when you'll want to reseed within a run of an application, in order to reproduce results, but this isn't one of them. [smile]

Hope I've explained it!
-jouley

[Edit: Beaten by the same information stated more succinctly and more. Oh, the Agony...]
Knew it was something simple

I must admit I didnt even look at that, so thanks alot guys. Changed that and put srand in main, and it works a treat now

Many thanks again

This topic is closed to new replies.

Advertisement