多线程下常用函数


前言

本文记录了某些常用函数


线程

线程是什么就不做过多介绍了

失败返回-1成功返回0
pthread_create(&tid, 0, worker, void*);
  -参数:
      线程号存放地址,线程属性,子线程运行的函数(cpp中需要为静态函数),函数的参数

线程属性

int pthread_attr_init(pthread_attr_t *attr);
    - 初始化线程属性变量

int pthread_attr_destroy(pthread_attr_t *attr);
    - 释放线程属性的资源

int pthread_attr_getdetachstate(const pthread_attr_t *attr, int *detachstate);
    - 获取线程分离的状态属性

int pthread_attr_setdetachstate(pthread_attr_t *attr, int detachstate);
    - 设置线程分离的状态属性

信号量

sem_t
sem_t sem; //创建一个信号量,相当于内部有一个倒计时的数字
sem_init
sem_init(&sem, 0, 0);
 int sem_init(sem_t *sem, int pshared, unsigned int value);
    - 初始化信号量
    - 参数:
        - sem : 信号量变量的地址
        - pshared : 0 用在线程间 ,非0 用在进程间
        - value : 信号量中的值
sem_destroy
sem_destroy(&sem);
-释放资源
sem_wait
sem_wait(&sem);
    int sem_wait(sem_t *sem);
    - 对信号量加锁,调用一次对信号量的值-1,如果值为0,就阻塞
sem_post
    int sem_post(sem_t *sem);
    - 对信号量解锁,调用一次对信号量的值+1

int sem_trywait(sem_t *sem);
int sem_timedwait(sem_t *sem, const struct timespec *abs_timeout);
int sem_getvalue(sem_t *sem, int *sval);

条件变量

满足某些条件时触发

pthread_cond_t
pthread_cond_t cond;
pthread_cond_init
pthread_cond_init(&cond);
pthread_cond_destroy
pthread_cond_destroy(&cond);
pthread_cond_wait
 pthread_cond_wait(&cond, &mutex);  //调用时mutex会暂时解锁,调用结束后再加锁
 int pthread_cond_wait(pthread_cond_t *restrict cond, pthread_mutex_t *restrict mutex);
    - 等待,调用了该函数,线程会阻塞。
pthread_cond_timedwait
pthread_cond_timewait(&cond, &mutex, )
int pthread_cond_timedwait(pthread_cond_t *restrict cond, 
                           pthread_mutex_t *restrict mutex, 
                           const struct timespec *restrict abstime);
    - 等待多长时间,调用了这个函数,线程会阻塞,直到指定的时间结束。
pthread_cond_signal
pthread_cond_signal(&cond);  //通知wait不阻塞
int pthread_cond_signal(pthread_cond_t *cond);
    - 唤醒一个或者多个等待的线程
pthread_cond_broadcast
int pthread_cond_broadcast(pthread_cond_t *cond);
    - 唤醒所有的等待的线程

互斥锁

用于保证线程同步,一个线程拿到锁后其它线程则处于阻塞状态,至到解锁

出现死锁的情况:

  • 忘记解锁
  • 重复加锁
  • 互相锁死对方

成功返回0,失败返回-1

pthread_mutex_t
pthread_mutex_t mutex; //定义一个锁  
pthread_mutex_init
pthread_mutex_init(&mutex, NULL);


    int pthread_mutex_init(pthread_mutex_t *restrict mutex, const pthread_mutexattr_t *restrict attr);
    - 初始化互斥量
    - 参数 :
        - mutex : 需要初始化的互斥量变量
        - attr : 互斥量相关的属性,NULL
    - restrict : C语言的修饰符,被修饰的指针,不能由另外的一个指针进行操作。
        pthread_mutex_t *restrict mutex = xxx;
        pthread_mutex_t * mutex1 = mutex;
   -	成功返回0,失败返回-1
pthread_mutex_destroy
释放互斥量的资源
pthread_mutex_destroy(&mutex);
pthread_mutex_lock
 pthread_mutex_lock(&mutex);
- 加锁,阻塞的,如果有一个线程加锁了,那么其他的线程只能阻塞等待
pthread_mutex_trylock
 pthread_mutex_trylock(&mutex);
 - 尝试加锁,如果加锁失败,不会阻塞,会直接返回。
pthread_mutex_unlock
pthread_mutex_unlock(&mutex);
-解锁

读写锁

    读写锁的类型 pthread_rwlock_t
int pthread_rwlock_init(pthread_rwlock_t *restrict rwlock, const pthread_rwlockattr_t *restrict attr);
int pthread_rwlock_destroy(pthread_rwlock_t *rwlock);
int pthread_rwlock_rdlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_tryrdlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_wrlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_trywrlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_unlock(pthread_rwlock_t *rwlock);

生产者消费者模型

在这里插入图片描述

// 创建一个互斥量
pthread_mutex_t mutex;
// 创建两个信号量
sem_t psem;
sem_t csem;

int container=0;

void * producer(void * arg) {
    // 不断的创建新的节点,添加到链表中
    while(1) {
        sem_wait(&psem);
        pthread_mutex_lock(&mutex);
        ++container;
        pthread_mutex_unlock(&mutex);
        sem_post(&csem);
    }
    return NULL;
}

void * customer(void * arg) {

    while(1) {
        sem_wait(&csem);
        pthread_mutex_lock(&mutex);
        --container;
        pthread_mutex_unlock(&mutex);
        sem_post(&psem);
    }
    return  NULL;
}

int main() {

    pthread_mutex_init(&mutex, NULL);
    sem_init(&psem, 0, 8);
    sem_init(&csem, 0, 0);

    // 创建5个生产者线程,和5个消费者线程
    pthread_t ptids[5], ctids[5];

    for(int i = 0; i < 5; i++) {
        pthread_create(&ptids[i], NULL, producer, NULL);
        pthread_create(&ctids[i], NULL, customer, NULL);
    }

    for(int i = 0; i < 5; i++) {
        pthread_detach(ptids[i]);
        pthread_detach(ctids[i]);
    }

    while(1) {
        sleep(10);
    }
    pthread_mutex_destroy(&mutex);
    pthread_exit(NULL);
    return 0;
}


总结

总结了C多线程中会回到的函数。

锁,用于线程同步;条件变量,在满足某些条件时(遇到signal)触发(wait不阻塞);信号量,wiat-1,post+1,两个信号量可用于设置容器的上限。

最后用信号量实现生产者消费者模型。

  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值