Looking for multithreading method and tutorial

Hi,

As you might have seen in the title, I'm looking for a good multithreading method and corresponding tutorial. I've searched the web, but there is too much out there for me to choose from.

I've read a tutorial about the process.h file and the Windows API, but I prefer a more standard way: winAPI threading is way to opaque for me due all its different types and renaming (I think Windows reshapes my code into a (for me) illegible, CAPS_LOCK'd monster which doesn't look like any 'normal' C++ code I've ever seen), and it is OS specific. So I considered the Boost library, but I would rather use a more standard C++ish method and I'm not a hardcore fan of external libraries.

I heard that C++11 has a thread.h, but I'm using Dev-C++ (which doesn't support C++11). Perhaps I could download only the header and use it without the rest of the update, but I'm not really sure copy/pasting a header is the way to go.

Does anyone know a good, simple and standard way of threading and its corresponding tutorial which fits in the standard C++ usage (not like winAPI) and which does not require me to download foreign header files? I'm not very sure about what I'm actually seeking for and not all requirements have to be met, there just there to specify my goal for a bit.

Ok, that was all I had to say. (You may breathe again now) Please leave a reply and have a nice day!

Kind regards,
Niels Meijer
I heard that C++11 has a thread.h, but I'm using Dev-C++ (which doesn't support C++11).

Then maybe this is a sign that you should think about getting a more updated IDE.
Perhaps I could download only the header and use it without the rest of the update, but I'm not really sure copy/pasting a header is the way to go.

Definitely not the way to go. You can't just download a few header files from some other compiler and use them in your old outdated compiler.
Does anyone know a good, simple and standard way of threading

My best advice would be to obtain a newer IDE that can compile a C++11 program. You could download the latest Code::Blocks IDE (with compiler) or the latest Visual C++ IDE. Both of these compilers should support the std::thread library.

The other option, since you don't want to use the Windows API would be to download and use the Boost::thread library. If I remember correctly the std::thread library was based on this library.
If you are going to keep using Dev-C++, Use the Orwell edition, It should support C++11, you can find it here:

http://sourceforge.net/projects/orwelldevcpp

Also redownload the compiler. Using the default download link should work well for both x86 and x64.

Should we put the link in the "Why we've deprecated Dev-C++" page?

Ah, let me say: C++11 does not just include some headers. It also needs editing of the compiler itself, so copy/pasting a C++11 header for use in a C++-03 compiler won't work, unless the header is C++03-compatible.
Last edited on
Here is an example:

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
#include <process.h>
#include <cstdio>

int time;

int calculate(void *crap) {
	while (1) {
		Sleep(1000);
		time++;
	}
}

int calculate_from_arg(void *arg) {
	// First you have to convert the void pointer to an int one
	int *number = (int*) arg;

	// Now you can make use of it
	time = *number;
	while (1) {
		Sleep(1000);
		time++;
	}
}

int main() {
	// If everything you want to do is to make a function run on a new thread you can
	_beginthread(calculate, 0, 0);

	// If you also need to pass an argument you could try
	int start_time = 5;
	_beginthread(calculate_from_arg, 0, (void*)&start_time);

	Sleep(5000);
	printf("%d seconds has passed\n", time);

	// ... 
Last edited on
Antares64, completely wrong and crashy test.
time = &number;
This won't even compile.
@EssGeEich: Sorry, that is a mistake I made, just change & to * . time = *number;
Last edited on
Yeah, but if you don't use mutexes or so you may be reading data at a bad time, for example while it is being written.

'time++' is not an atomic part of code.
'++time' neither.

So, you cannot assume you can always read 'time' when another write operation on 'time' is being executed.

For small-scale tests it's all right, but be aware to this kind of things.

Also using globals isn't the best of things, an better example, still not using mutexes, looks like follows:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
int Parameter = 0;
_beginthread(calculate_from_arg, 0, &Parameter);
Sleep(5500); // Make sure you're not on a '1000' multiplier as the thread updates each 1000 ms
printf("%d seconds has passed\n", Parameter);

// and in calculate_from_arg...

int *number = (int*)arg;

while (1) {
	Sleep(1000);
	++(*number);
}
Last edited on
multithreading is a sexy clunky way of handling problems:

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
68
69
70
71
72
#include <Windows.h>

static bool g_bRunning = false;
static bool g_bLocked  = true;

bool isLocked()
{
  return g_bLocked;
}

void lock( bool bLocked )
{
  g_bLocked = bLocked;
}

unsigned long __stdcall someThread( void* someToken )
{
   int* pItemInt = reinterpret_cast<int*>( someToken );
 
   if( !pItemInt ) ExitThread( -1 );

  while(!g_bRunning && isLocked() );//wait until ready

  while( g_bRunning )
  {
     if( !isLocked() )
    {
         //do stuff, manipulate the pointer
        (*pItemInt) ++;

       lock( true );
    }
  }

  ExitThread( 0 );
}

int main()
{
  int token  =0;
  void* hThread = 0;
  unsigned long hThreadID = 0;

  hThread =  (void*)CreateThread( 0, 0, (LPTHREAD_START_ROUTINE)&someThread, 
 (HANDLE)&token, sizeof(token), 0, (DWORD)&hThreadID );

  if( !hThread || !hThreadID ) return -1;

 g_bRunning = true;

 while( g_bRunning  )
 {
    //do stuff here, this is higher priority then the thread
    if( token >= 1000 ) g_bRunning = false;

    //then free for the thread
    lock( false );

    Sleep( 16 );  

    while( !isLocked( ) );

    lock( true );
}

 printf("token:%d\n", token );

 WaitForSingleObject( hThread, INFINITE );
 CloseHandle( hThread );

 return 0;
}


In layman's terms, multithreading divides the time of the program's main process into a subroutine known as a thread. You pass data to the thread, prototypes and calling conventions of said thread functions are generally the same but can vary. Basically you gather the data you want to share with the thread and operate upon the data in that said thread. You want to avoid deadlocks and race conditions, where the data that you use influences the output of the program before it is supposed to. A deadlock completely halts the flow of the program and it is generally caused by a logic or timing error.

I made a digital timer using multithreading. It logged the day, month, year, hour, second, etc. Multhreading is good if something takes so much time that it stalls your main thread greater than or equal to 1 second.
Last edited on
Topic archived. No new replies allowed.