I'd argue that multithreading in C++ is not a beginner topic. There are lots of nuances that are very easy to get wrong if you're not extremely careful.
Case in point... in Stormboy's extremely simplistic example... he does not do any synchornization, so if you do that code, you will get corrupted/unexpected output due to race conditions in your threads. You'll see things like:
Random number is: Color changed to: 63Blue
!
Color changed to: BlueRandom number is!
156
(etc)
|
Most of the time... updating multiple things "at once" is better accomplished serially rather than in parallel.
EDIT:
To elaborate... when I say "do things serially", I mean have one thread that switches between doing multiple things. Rather than creating a new thread for each thing you want to do.
A common pitfall for newbies is that they tend to make all of their code 'blocking'. This means it waits for some action to finish before allowing any further code to execute.
Here's an example (using WinAPI's 'Sleep' function. I'm too lazy to look up the C++11 equivalent... but hopefully you get the idea):
1 2 3 4 5 6 7 8 9
|
int main()
{
// print a countdown:
for(int x = 5; x >= 0; --x)
{
cout << x << endl;
Sleep(1000); // wait for 1 second.
}
}
|
This will print a new number every second, until 0 is reached.
And while this
works... it is blocking. Which means your program cannot do anything else while this countdown is happening.
A non-blocking approach would be to not Sleep... but instead periodically poll the time. Again I'm too lazy to look up the actual code for this so here is pseudo-code:
And I just slapped this together. This could probably be cleaner:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
|
int main()
{
int countdown = 5;
cout << countdown << endl;
auto lastPrintTime = getTheCurrentTime();
while( countdown >= 0 )
{
// see if it has been a second since the last time we printed
auto now = getTheCurrentTime();
if( now - lastPrintTime > oneSecond )
{
// it has been... so count down
--countdown;
cout << countdown << endl;
lastPrintTime = now;
}
// then do something else
doSomethingElse();
}
}
|
In this example... we have the same countdown... that waits 1 second between printing updates... but we're not blocked. doSomethingElse is
repeatedly being called during the countdown, which will allow you to do something else while the countdown is happening.
It's all about shifting your design. Adding threads can be helpful in some situations, but usually they add a lot more complication and bugs than they're worth.