The codes are from Multithreading Applications in Win32 written by Jim Beveridge & Robert Wiener First, please study the second and sixth parameters. unsigned long _beginthreadex( void *security, unsigned stack_size, unsigned (* start_address)(void *), void *arglist, unsigned initflag, unsigned *thrdaddr); HANDLE CreateThread( LPSECURITY_ATTRIBUTES lpThreadAttributes, DWORD dwStackSize, LPTHREAD_START_ROUTINE lpStartAddress, LPVOID lpParameter, DWORD dwCreationFlags, LPDWROD lpThreadId); According to Jim Beveridge & Robert Wiener' point of view, the function _beginthreadex() is the coat of CreateThread() and the types of its parameters have been changed for the sake of being adoptable to other operation system. While, as the CloseHandle() must be called at last, programmers can't get rid of "window.h". Another side effect is, though C compiler makes no difference between DWORD and unsigned (in fact unsigned int), C++ compiler doen't think so. As CreateThread() is inside _beginthreadex(), its parameters are less likely to be modified. Defining parameters according to CreateThread() is smarter. Since the parameters must be accepted by _beginthreadex(), the codes we discussing must appear there. The true meaning of the codes is: force type convertion before calling _beginthreadex(). the following are codes in all: //The beginning of codes #define WIN32_LEAN_AND_MEAN #include #include #include #include typedef unsigned (WINAPI *PBEGINTHREADEX_THREADFUNC)( LPVOID lpThreadParameter ); typedef unsigned *PBEGINTHREADEX_THREADID; int main() { HANDLE hThread; DWORD dwThreadId; int i=0; hThread = (HANDLE) _beginthreadex(NULL, 0, (PBEGINTHREADEX_THREADFUNC)ThreadFunc, // Attention, Plz (LPVOID) i, 0, (PBEGINTHREADEX_THREADID) & dwThreadId // Attention, Plz ); if(hThread) { WaitForSingleObject(hThread, INFINITE); CloseHandle(hThread); } return EXIT_SUCCESS; } DWORD WINAPI ThreadFunc(LPVOID n) { // Do something... return 0; } //The end of codes My opinion