线程的同步与互斥

抢票的例子

线程的同步与互斥_第1张图片

竞争过程

线程的同步与互斥_第2张图片

进程A被切走

线程的同步与互斥_第3张图片

进程B被切走

线程的同步与互斥_第4张图片

结论:

线程的同步与互斥_第5张图片

互斥

int pthread_mutex_init(pthread_mutex_t *mutex, const pthread_mutexattr_t *attr);
  • mutex: 指向要初始化的互斥锁的指针。
  • attr: 用于设置互斥锁属性的指针,通常可以传入 NULL 以使用默认属性。

线程的同步与互斥_第6张图片

线程的同步与互斥_第7张图片

锁的本质

加锁

线程的同步与互斥_第8张图片

线程的同步与互斥_第9张图片

解锁

线程的同步与互斥_第10张图片

线程的同步与互斥_第11张图片

线程安全与重入

线程的同步与互斥_第12张图片

线程的同步与互斥_第13张图片

死锁

线程的同步与互斥_第14张图片

线程同步

线程的同步与互斥_第15张图片

生产消费模型

线程的同步与互斥_第16张图片

例子

线程的同步与互斥_第17张图片

条件变量

线程的同步与互斥_第18张图片

demo

#include
#include
#include
#include

int tickets=1000;
pthread_mutex_t mutex=PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t cond=PTHREAD_COND_INITIALIZER;

void *start_routine(void* args){
    std::string name=static_cast(args);
    while(true){
        pthread_mutex_lock(&mutex);
        pthread_cond_wait(&cond,&mutex);
        std::cout<"<

线程的同步与互斥_第19张图片

线程的同步与互斥_第20张图片

信号量

线程的同步与互斥_第21张图片

线程的同步与互斥_第22张图片

常用函数

线程的同步与互斥_第23张图片

环形队列

线程的同步与互斥_第24张图片

环形队列代码

#include"RingQueue.hpp"
#include
#include
#include
#include

void *ProductorRoutine(void* rq){
    RingQueue *ringqueue=static_cast*>(rq);
    while(true){
        int data=rand()%10+1;
        ringqueue->Push(data);
        std::cout<<"生产完成 生产的数据是:"< *ringqueue=static_cast*>(rq);
    while(true){
        int data;
        ringqueue->Pop(data);
        std::cout<<"消费完成 消费数据是:"< *rq=new RingQueue();
    pthread_t p,c;

    pthread_create(&p,nullptr,ProductorRoutine,rq);
    pthread_create(&c,nullptr,ConsumerRoutine,rq);

    pthread_join(p,nullptr);
    pthread_join(c,nullptr);

}
#include
#include
#include
#include
#include

static const int gcap=5;

template
class RingQueue{
public:
    void P(sem_t &sem){
        int n=sem_wait(&sem);
        assert(n==0);
        (void)n;
    }

    void V(sem_t &sem){
        int n=sem_post(&sem);
        assert(n==0);
        (void)n;
    }

public:
    RingQueue(const int &cap=gcap):_q(cap),_cap(cap){
        int n=sem_init(&_spaceSem,0,_cap);
        assert(n==0);
        n=sem_init(&_dataSem,0,0);
        assert(n==0);

        productorStep=ConsumerStep=0;
    }

    void Push(const T &in){
        P(_spaceSem);
        _q[productorStep++]=in;
        productorStep%=_cap;
        V(_dataSem);
    }

    void Pop(T &out){
        P(_dataSem);
        out=_q[ConsumerStep++];
        ConsumerStep%=_cap;
        V(_spaceSem);
    }

    ~RingQueue(){
        sem_destroy(&_spaceSem);
        sem_destroy(&_dataSem);
    }
    private:
    std::vector _q;
    int _cap;
    sem_t _spaceSem;  //生产者 空间资源
    sem_t _dataSem;   //消费者 数据资源
    int productorStep;
    int ConsumerStep;
};

你可能感兴趣的:(开发语言)