用互斥锁和条件变量

#include<stdio.h>
#include<semaphore.h>
#include <pthread.h>
#include<unistd.h>
#include<string.h>

//标志位条件变量
int flag=0;

pthread_cond_t cond;//条件变量参数值

pthread_mutex_t mutex;//创建锁

void *callBack(void *arg)                                                                           
{
    int n=0;//函数打印次数,也是退出死循环条件arg
    while(1)
    {
        //要求打印一次退出一次,下次再进来打印时算作第二次,
        //10次完成后线程结束,再次跳转下一个线程
        /***临界区***/
        pthread_mutex_lock(&mutex);//上锁
        if(flag==0)//符合条件变量进入
        {
            printf("A\n");//n只要是10以内进来一次打印一次
            flag=1;
                n++;
            if(n==10){
                pthread_mutex_unlock(&mutex);
                break;//n>10,直接退出循环,执行唤醒程序
            }
        }
        else//不符合条件变量沉睡并解锁
        {
            pthread_cond_wait(&cond,&mutex);
            //1,不符合条件flag==0,沉睡进程,沉睡在cond上
            //2.若是被唤醒,从此位置继续往下执行
            //3.若是没有被唤醒,将会继续沉睡(即线程执行到signal
        }
    pthread_cond_signal(&cond);//唤醒函数这里退出循环以后唤醒其他程序
    pthread_mutex_unlock(&mutex);//解锁
    }
    pthread_exit(NULL);//n>10结束线程
}
void *callBack1(void *arg)                                                                           
{
    int n=0;//函数打印次数,也是退出死循环条件
    while(1)
    {
        //要求打印一次退出一次,下次再进来打印时算作第二次,
        //10次完成后线程结束,再次跳转下一个线程
        /***临界区***/
        pthread_mutex_lock(&mutex);//上锁
        if(flag==0)//符合条件变量进入
        {
            printf("B\n");//n只要是10以内进来一次打印一次
            flag=1;
                n++;
            if(n==10){
                pthread_mutex_unlock(&mutex);
                break;//n>10,直接退出循环,执行唤醒程序
            }
        }
        else//不符合条件变量沉睡
        {
            pthread_cond_wait(&cond,&mutex);
            //1,不符合条件flag==0,沉睡进程,沉睡在cond上
            //2.若是被唤醒,从此位置继续往下执行
            //3.若是没有被唤醒,将会继续沉睡(即线程执行到signal
        }
    pthread_cond_signal(&cond);//唤醒函数//这里退出循环以后唤醒其他程序
    pthread_mutex_unlock(&mutex);//解锁
    }
    pthread_exit(NULL);//n>10结束线程
}
void *callBack2(void *arg)                                                                           
{
    int n=0;//函数打印次数,也是退出死循环条件
    while(1)
    {
        //要求打印一次退出一次,下次再进来打印时算作第二次,
        //10次完成后线程结束,再次跳转下一个线程
        /***临界区***/
        pthread_mutex_lock(&mutex);//上锁
        if(flag==2)//符合条件变量进入
        {
            printf("C\N");//n只要是10以内进来一次打印一次
            flag=0;
            n++;
            if(n==10){
                pthread_mutex_unlock(&mutex);
                break;//n>10,直接退出循环,执行唤醒程序
            }
        }
        else//不符合条件变量沉睡
        {
            pthread_cond_wait(&cond,&mutex);
            //1,不符合条件flag==0,沉睡进程,沉睡在cond上
            //2.若是被唤醒,从此位置继续往下执行
            //3.若是没有被唤醒,将会继续沉睡(即线程执行到signal
        }
    pthread_cond_signal(&cond);//唤醒函数//这里退出循环以后唤醒其他程序
    pthread_mutex_unlock(&mutex);//解锁
    }
    pthread_exit(NULL);//n>10结束线程
}

int main(int argc, const char *argv[])
{
    //创建条件变量
    if(pthread_cond_init(&cond,NULL)!=0)
    {
        perror("pthread_cond_init");
        return -1;
    }
    //创建锁
    if(pthread_mutex_init(&mutex,NULL)!=0)
    {
        perror("pthread_mutex_init");
        return -1;
    }

    //创建俩条线程                                                                                  
    pthread_t tid1,tid2,tid3;
    if(pthread_create(&tid1,NULL,callBack,NULL)!=0)
    {
        perror("pthread_create");
        return -1;
    }
    if(pthread_create(&tid2,NULL,callBack1,NULL)!=0)                                        
    {
        perror("pthread_create");
        return -1;
    }
    if(pthread_create(&tid3,NULL,callBack2,NULL)!=0)                                         
    {
        perror("pthread_create");
        return -1;
    }
    //回收线程数据
    pthread_join(tid1,NULL);
    pthread_join(tid2,NULL);
    pthread_join(tid3,NULL);

    //销毁锁
    pthread_mutex_destroy(&mutex);
    //销毁条件变量
    pthread_cond_destroy(&cond);

    return 0;
}
 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值