c - 如何使用互斥体同步多个线程?

标签 c linux multithreading pthreads mutex

我是一名学习者,正在尝试积累多线程编程的知识。特别是,我想了解如何将互斥体与 pthreads 一起使用。

#include<stdio.h>
#include<pthread.h>
pthread_mutex_t x,y;
static int p=0;
void print(char *x)
{
        p++;
        printf("%d ------ %s\n",p,x);
}
void * thread_1(char *m)
{
        int i;
        for(i=1;i<=10;i++)
        {
                print(m);
        }
}

void * thread_2(char *m)
{
        int i;
        sleep(1);
        for(i=1;i<=10;i++)
        {
                print(m);
        }

}
int main()
{

        pthread_t t1;
        pthread_t t2;
        pthread_mutex_init(&y,NULL);
        pthread_mutex_init(&x,NULL);
        pthread_create(&t1,NULL,thread_1,"thread_1");
        pthread_create(&t2,NULL,thread_2,"thread_2");

        while(1);
}

我创建了两个线程,现在我正在尝试同步它们。我应该在哪里使用两个互斥体锁定和解锁?

我想这样输出:

1 ----- thread_1  
2 ----- thread_2   
3 ----- thread_1   
4 ----- thread_2   
5 ----- thread_1   
6 ----- thread_2    
7 ----- thread_1   
8 ----- thread_2     
9 ----- thread_1        
10 ----- thread_2   
11 ----- thread_1   
12 ----- thread_2   
13 ----- thread_1   
14 ----- thread_2   
15 ----- thread_1   
16 ----- thread_2   
17 ----- thread_1   
18 ----- thread_2   
19 ----- thread_1   
20 ----- thread_2

最佳答案

这当然可以使用互斥体来完成,但一对信号量更适合此任务。使用两个信号量,每个信号量与一个线程关联,该线程向另一个线程发送消息以通知其轮流。 请注意,线程函数采用 void*,而不是 char*

void * thread_1(void *m)
{
        int i;
        for(i=1;i<=10;i++)
        {
                sem_wait(&sem2);
                print(m);
                sem_post(&sem1);
        }
}

void * thread_2(void *m)
{
        int i;
        for(i=1;i<=10;i++)
        {
                sem_wait(&sem1);
                print(m);
                sem_post(&sem2);
        }
}

int main(void) {
 ...
 sem_init(&sem1, 0, 0);
 sem_init(&sem2, 0, 1);
 ...
}

sleep() 调用是不必要的。您也不需要在 main() 线程中有无限循环。如果您希望线程完成,请使用pthread_join()。或者直接调用 pthread_exit(0); 而不是 while(1);

<小时/>

使用互斥体和条件变量对,在线程之间交替使用另一个变量来通知轮次。本质上与上面的逻辑相同,但对于这个任务来说有点“繁重”。我不知道为什么你“必须”使用互斥体:(

pthread_cond_t cond = PTHREAD_COND_INITIALIZER;
pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
int turn = 0;

void print(char *x)
{
        p++;
        printf("%d ------ %s\n",p,x);
}
void * thread_1(void *m)
{
        int i;
        for(i=1;i<=10;i++)
        {
           pthread_mutex_lock(&mutex);
           while (turn != 0)
              pthread_cond_wait(&cond, &mutex);
           print(m);
           turn = 1;
           pthread_cond_signal(&cond);
           pthread_mutex_unlock(&mutex);
        }
}

void * thread_2(void *m)
{
        int i;
        for(i=1;i<=10;i++)
        {
            pthread_mutex_lock(&mutex);
            while (turn != 1)
               pthread_cond_wait(&cond, &mutex);
            print(m);
            turn = 0;
            pthread_cond_signal(&cond);
            pthread_mutex_unlock(&mutex);
        }
}

关于c - 如何使用互斥体同步多个线程?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35194940/

相关文章:

你能用 C#define 注释吗?

C 从字符串的一部分获取数值

c - 将用户输入的日期加上 7 天的日期计算程序

c - 我应该如何将变量传递给 system() C 调用?

c - Linux等待队列——独占和非独占的结合

c - 动态分配的段错误

linux - 如何(分别)查找所有目录和子目录的文件总和,并按大小对它们进行排序

linux - Linux 上是否还存在 Thundering Herd 问题?

java - 我们需要在 ScheduledExecutorService 上调用 awaitTermination 吗?

org.apache.catalina.connector.Request.setAttribute 中的 java.lang.NullPointerException