我认为您所描述的不是一个好主意:您将如何管理由于某些错误而未创建线程的情况?
pthread_cond_wait 可能是一个优雅的解决方案,但您应该为 5 个线程中的每一个使用等待条件;加上一个条件更像是一个触发器:当某事发生时,做某事。根据您的描述,您想要一些更像初始条件的东西。
一个简单的解决方案是使用一个作为计数器的全局变量,每次创建 5 个线程中的一个时,计数器都会递增:
无论如何,要查看是否正确创建了线程,您可以使用以下内容:
if ((err = pthread_create (&threadID, NULL, threadFunction, NULL))!=0)
{
printf("some error\n");
}
else
{
global_counter++;
}
然后在每个线程函数中,使用一个什么都不做的循环,它的循环条件检查计数器变量是否小于你要创建的线程数:
while (global_counter<5)
{
;
}
..../rest of the thread functions
注意:这是危险的,因为如果您在选择变量值时不小心,您会陷入 5 个无限循环。
您还应该使用某种类型的互斥锁(可能是读/写互斥锁),因为全局计数器由一个线程写入并由多个线程读取。
重要编辑:您还应该管理未创建线程之一的情况(例如杀死已经创建的线程而不创建其他线程),否则其他线程将再次陷入困境无限循环。
编辑 2
我知道这是很久以前问过的,但实际上还有其他解决方案,也许更优雅。
一个是在您的问题中使用pthread_cond_wait() 在必须等待初始化的线程中和pthread_cond_broadcoast()/pthread_cond_signal() 在初始化线程中的位置。
pthread_cond_signal 和pthread_cond_broadcast 的区别如下:前者是单线程获取锁并执行。其他人还需要等待。使用pthread_cond_broadcast,所有线程将同时解除阻塞。例如:
pthread_mutex_t mtx;
pthread_cond_t cv;
void* threadFunction(void*);
int main()
{
pthread_mutex_lock(&mtx);
for (int i=0; i<5; i++)
{
if ((err = pthread_create (&threadID, NULL, threadFunction, NULL))!=0)
{
printf("some error\n");
}
}
pthread_cond_broadcast(&cv);
pthread_mutex_unlock(&mtx);
}
void* threadFunction(void*)
{
pthread_mutex_lock(&mtx);
pthread_cond_wait(&cv, &mtx);
do_things();
pthread_mutex_unlock(&mtx);
}
我认为另一种解决方案是使用写锁和写锁:在开头main thread 在写时锁定一个读写互斥锁。其他线程将尝试将其锁定(例如,如果您想同时唤醒它们,则在读取模式下),但存在写入锁定它们将被阻止。
创建所有线程后,main 解锁,其他线程可以执行:
pthread_rwlock_t lock;
void* threadFunction(void*);
int main()
{
pthread_rwlock_init(&lock, ...);
//First acquire the write lock:
if ((res = pthread_rwlock_wrlock(&lock)!=0)
{
exit(1);
}
for (int i=0; i<5; i++)
{
if ((err = pthread_create (&threadID, NULL, threadFunction, NULL))!=0)
{
printf("some error\n");
}
}
pthread_rwlock_unlock(&lock);
pthread_rwlock_destroy(&lock);
}
void* threadFunction(void*)
{
pthread_rwlock_rdlock(&lock);
do_things();
pthread_rwlock_unlock(&lock);
}