我正在尝试同时运行3个线程,然后在主线程中检测到哪个线程已完成。我正在使用WaitForMultipleObject函数,但第三个线程似乎为这个WFMO函数循环,而它已经完成了它的工作(打印结果)。
#include <Windows.h>
#include <stdio.h>
#include <conio.h>
//---------------------------------------------------------------------------
#pragma argsused
struct data
{
char name[50];
} data[3] = { { "[THREAD 0]" }, { "[THREAD 1]" },{ "[THREAD 2]" } };
DWORD WINAPI th0()
{
//here are some calculations
//also added 1s sleep
//printing result
return 0;
}
DWORD WINAPI th1()
{
//here are some other calculations
//also added 1s sleep
//printing result
return 0;
}
DWORD WINAPI th2()
{
//here are some other simple calculations
//also added 1s sleep
//printing result
return 0;
}
int priority[3] = { 0,0, 0};
HANDLE threads[3];
HANDLE functions[3];
int main(int argc, char **argv)
{
int i;
DWORD id; // thread's id
printf("Program started...\n");
functions[0] = th0;
functions[1] = th1;
functions[2] = th2;
for (i = 0; i < 3; i++)
{
threads[i] = CreateThread(
NULL, // security atributes
0, // stack size
(LPTHREAD_START_ROUTINE)functions[i], // threads
NULL,// input data for threads
0, // creation's flags
&id);//thread's id
if (threads[i] != INVALID_HANDLE_VALUE)
{
printf("Created thread %s with ID: %x\n",
data[i].name, id);
SetThreadPriority(threads[i], priority[i]);
}
}
bool f0=false, f1=false, f2=false;
while(!f0 || !f1 || !f2)//while there is any unfinished thread
{
DWORD wfmo = WaitForMultipleObjects(3, threads, false, INFINITE);
if (!f0 && WAIT_OBJECT_0==wfmo)
{
printf("%s is done!\n", data[0].name);
f0=true;
//CloseHandle(threads[0]);
//threads[0]=NULL;
}
if (!f1 && WAIT_OBJECT_0 +1 == wfmo)
{
printf("%s is done!\n", data[1].name);
f1=true;
//CloseHandle(watki[1]);
//watki[1]=NULL;
}
if (!f2 && WAIT_OBJECT_0 +2 == wfmo)
{
printf("%s is done!\n", data[2].name);
f2=true;
//CloseHandle(threads[2]);
//threads[2]=NULL;
}
if(wfmo==WAIT_TIMEOUT)
printf("timeout\n");
if(wfmo==WAIT_FAILED)
printf("failed\n");
}
//Sleep(20000); //20s
return 0;
}
输出:
Program started...
Created thread [THREAD 0] with ID: b00
Created thread [THREAD 1] with ID: a64
Created thread [THREAD 2] with ID: 7d0
[THREAD 2] Result: 131072
[THREAD 1] Result: 121393
[THREAD 0] Result: 362880
[THREAD 2] is done!
[THREAD 0] is done!
答案 0 :(得分:0)
来自MSDN WaitForMultipleObjects
文档:
如果bWaitAll为FALSE,则返回值减去WAIT_OBJECT_0表示满足等待的对象的lpHandles数组索引。如果在调用期间发出多个对象的信号,则这是信号对象的数组索引,其中所有信号对象的索引值最小。
线程0完成后,返回值将始终为WAIT_OBJECT_0
。
答案 1 :(得分:0)
解决方案(而不是while循环):
DWORD wfmo = WaitForMultipleObjects(3, threads, false, INFINITE);
//HANDLE threads2[2];
if ( WAIT_OBJECT_0==wfmo)//move th1 and th2 up
{
printf("%s is done!\n", data[0].name);
threads[0]=threads[1];
threads[1]=threads[2];
data[0]=data[1];
data[1]=data[2];
threads[2]=NULL;
}
else if ( WAIT_OBJECT_0 +1 == wfmo) //move th2 up
{
printf("%s is done!\n", data[1].name);
threads[1]=threads[2];
data[1]=data[2];
threads[2]=NULL;
}
else if ( WAIT_OBJECT_0 +2 == wfmo)//no need to do anything
{
printf("%s is done!\n", data[2].name);
threads[2]=NULL;
}
wfmo = WaitForMultipleObjects(2, threads, false, INFINITE);
if ( WAIT_OBJECT_0==wfmo)
{
printf("%s is done!\n", data[0].name);
threads[0]=threads[1];
data[0]=data[1];
threads[1]=NULL;
}
else if ( WAIT_OBJECT_0 +1 == wfmo)
{
printf("%s is done!\n", data[1].name);
threads[1]=NULL;
}
wfmo = WaitForMultipleObjects(1, threads, false, INFINITE);
if ( WAIT_OBJECT_0==wfmo)
printf("%s is done!\n", data[0].name);