POSIX信号量

本文介绍了POSIX信号量作为临界资源的管理工具,用于线程间同步,确保无冲突地访问共享资源。信号量通过P操作(减一)和V操作(加一)来控制对资源的访问。文中提到了初始化、销毁、等待和发布信号量的相关函数,并以生产者-消费者问题为例,展示了基于环形队列和POSIX信号量的实现,演示了如何协调生产者和消费者的同步行为。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

  • 信号量是一种临界资源,它的本质是计数器。
  • 信号量的基本操作有两种:P操作和V操作。P操作相当于给计数器减一,V操作相当于给计数器加一。
  • 信号量描述了其所要保护的临界资源的数目。因为信号量本身也是一种临界资源,所以我们用它去保护其他临界资源的前提是要保证信号量自身操作的原子性。
  • POSIX信号量和SystemV信号量作用相同,都是用于同步操作,达到无冲突的访问共享资源的目的。单POSIX可以用于线程间同步。
  • 信号量P操作成功,表示允许访问临界资源。

有关信号量的常见函数:

1、初始化信号量

函数原型:int   sem_init(sem_t   *sem,int   pshared,unsigned   int   value);

参数:

pshared:0表示线程间共享,非零表示进程间共享。

value:信号量初始值

2、销毁信号量

函数原型:int   sem_destroy(sem_t   *sem);

3、等待信号量

函数原型:int   sem_wait(sem_t   *sem);

功能:等待信号量,会将信号量的值减一,相当于对信号量进行P操作。

4、发布信号量

函数原型:int   sem_post(sem_t   *sem);

功能:发布信号量,表示资源使用完毕,可以归还资源了。将信号量的值加一,相当于对信号量进行V操作。

  • 生产者-消费者的例子是基于链表的,其空间可以动态分配,现在基于固定大小的环形队列重写这个程序(POSIX信号量):

#include<unistd.h>
#include<sys/types.h>
#include<pthread.h>
#include<semaphore.h>
#include<stdio.h>
#include<stdio.h>
#include<errno.h>
#include<string.h>

#define M 6

int ring[M];
sem_t semBlank,semData;

void* runC(void *arg){
    int i = 0;
    int d;
    while(1){
        sem_wait(&semData);
        d = ring[i];
        i++;
        i %= M;
        printf("comsumer done , data is %d\n",d);
        sem_post(&semBlank);
        sleep(1);
    }
}
void* runP(void* arg){
    int d = 0;
    int i = 0;
    while(1){
        sem_wait(&semBlank);
        ring[i] = rand()%123+1;
        d = ring[i];
        i++;
        i %= M;
        printf("product done , data is %d\n",d);
        sem_post(&semData);
    }
}
int main(){
    sem_init(&semBlank,0,M);
    sem_init(&semData,0,0);

    srand((unsigned long)time(NULL));
    pthread_t t1,t2;
    pthread_create(&t1,NULL,runC,NULL);
    pthread_create(&t2,NULL,runP,NULL);

    pthread_join(t1,NULL);
    pthread_join(t2,NULL);

    sem_destroy(&semBlank);
    sem_destroy(&semData);
}

结果演示:


通过结果我们可以看出,生产者先生产一些数据,等到生产者生产的数据占满整个环形队列时,生产者就停止生产,直到有消费者拿走数据。此时消费者拿走一条数据,生产者就生产一条数据。



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值