信号量PV操作

基本介绍

  • 信号量(Semaphore):是表示资源的实体,是一个与队列有关的整型变量,其值仅能由P、V操作改变。
  • 信号量分为:公用信号量和私用信号量。
  • 公用信号量:用于实现进程间的互斥,初值通常设为1,它所联系的一组并发进程均可对它实施P、V操作;
  • 私用信号量:用于实现进程间的同步,初始值通常设为0或n,允许拥有它的进程对其实施Р操作。

数据结构

信号量的数据结构:

struct semaphore{
int value; //系统中的资源数
pointer_PCB queue; //阻塞进程队列
};//PCB表示进程控制块
//声明
semaphore s;

PV操作

P(s){//申请资源
if(--s.value<0){
该进程设置为阻塞态
将该进程的PCB插入阻塞队列s.queue末尾
}
}
V(s){//释放资源
if(++s.value <= 0){
唤醒相应阻塞队列s.queue中等待的一个进程
改变其状态为就绪态
并将其插入就绪队列
}
}

s. value >= 0时,其值表示还有可用的资源数;

s. value < 0时,其绝对值表示有多少个进程因申请该信号量表示的资源,得不到而进入阻塞态;

解决进程互斥问题

把P1-P3进程的互斥操作包括在一个PV操作对中

由P2进入

举例1:

启发:写并发进程的时候需要明确互斥区

  1. 不同进程未进入互斥区时可以并发
  2. 不同进程进入互斥区时要用PV操作控制

解决进程同步问题

在同步问题中信号量的value值相比于“资源”资源来说,理解为“权限”会更合适,在一个同步问题中,一个进程的执行权限是由它的前驱进程赋予的

代码实现(以同步问题为例)

为了便于实现,将程序的运行操作也封装到PV操作中,即

  • 如果P操作为信号量申请到权限,那么直接执行信号量所对应的进程
  • 如果V操作赋予了信号量权限且信号量的阻塞队列中有进程,那么直接执行阻塞队列中的进程

代码如下:【本人才疏学浅,如有不足恳请斧正】

#include<iostream>
#include<string>
#include<queue>
using namespace std;
/*定义类:process表示一个进程*/
class process{
public :
/*构造函数*/
process() = default;
process(const string &name) : process_name(name){}
process(const process &p) :
process_name(p.process_name){}
/*成员函数*/
//执行进程
void _on(){cout<<process_name+": on"<<endl;}
//关闭进程
void _off() {cout<<process_name+": of"<<endl;}
//进程名
string process_name;
}; /*定义类:semaphore表示信号量*/
/*一个信号量控制一个进程*/
class semaphore{
/*友元声明:确保PV操作可以访问semaphore私有成员*/
friend void P(semaphore &s);
friend void V(semaphore &s);
public:
/*构造函数:参数为信号量控制的进程*/
semaphore(const process &p) :
present(p){};
private :
int value = 0; //同步问题value初始化为0
process present; //该信号量控制的进程
queue<process> blocked_processes; //阻塞队列
}; /*P操作:申请资源(权限)*/
void P(semaphore &s){
--s.value;//申请
if(s.value<0){//无资源(权限):进程进入阻塞队列
//打印提示信息
cout<<s.present.process_name+" is blocked"<<endl;
//将进程加入阻塞队列
s.blocked_processes.push(s.present);
}
else{//有资源:直接执行
s.present._on();
}
}
/*V操作:返回资源(给予权限)*/
void V(semaphore &s){
++s.value;//赋予
if(s.value>=0){//如果阻塞队列有进程:唤醒阻塞进程
if(!s.blocked_processes.empty()){
s.blocked_processes.front()._on();
s.blocked_processes.pop();
}
}
//否则什么也不做
}
//开车进程
process speed_up("speed_up");
//开门进程
process open_door("open_door");
//用两个信号量分别控制开车进程和开门进程
semaphore OpenDoor(open_door), Speed_Up(speed_up); int main(){
V(OpenDoor); //赋予开车门的权限
P(OpenDoor); //申请权限:有权限,可以开,打印open_door: on
P(OpenDoor); //申请权限:无权限,开不了门,进入开门阻塞队列
P(Speed_Up); //申请权限:无权限,开不了车,进入开车阻塞队列
V(Speed_Up); //赋予权限:执行开车阻塞队列进程,打印speed_up: on
V(OpenDoor); //赋予权限:执行开门阻塞队列进程,打印open_door: on
return 0;
}

运行结果:

进程相互作用之信号量PV操作及其代码实现的更多相关文章

  1. Linux下IPC中的信号量PV操作

    代码如下所示,两边对照查看程序!(左图为先运行进程 右图为后运行进程)    运行的效果就是:当左边的进程检测到EOF,释放资源V操作之后,右边的进程会迅速的执行对应的printf的操作! 所有代码文 ...

  2. linux下的信号量PV操作进阶之路

    一.同步和互斥机制 信号量 互斥锁 同步:指多个任务按照约定的先后次序相互配合来完成一件事情. 比如读线程等待写线程写完之后再去读. 二.信号量-P/V操作 P(s)含义: if(信号量>0) ...

  3. java信号量PV操作 解决生产者-消费者问题

    package test1; /** * 该例子演示生产者和消费者的问题(设只有一个缓存空间.一个消费者和一个生产者) * MySystem类定义了缓冲区个数以及信号量 * @author HYY * ...

  4. Operating System-进程/线程内部通信-信号量和PV操作

    本文介绍操作系统进程管理的两个核心概念: 信号量 PV操作 一.信号量介绍 1.1 信号量引入 信号量(Semaphore)1965年由Dijkstra引入的.信号量一般由一个值是一个变量,其值有可能 ...

  5. 信号量与PV操作

    在计算机操作系统中,PV操作是进程管理中的难点.首先应弄清PV操作的含义:PV操作由P操作原语和V操作原语组成(原语是不可中断的过程),对信号量进行操作,具体定义如下:    P(S):①将信号量S的 ...

  6. Pintos修改优先级捐赠、嵌套捐赠、锁的获得与释放、信号量及PV操作

    Pintos修改优先级捐赠.嵌套捐赠.锁的获得与释放.信号量及PV操作 原有的优先级更改的情况下面没有考虑到捐赠的情况,仅仅只是改变更改了当前线程的优先级,更别说恢复原本优先级了,所以不能通过任何有关 ...

  7. 信号量和PV操作写出Bakery算法的同步程序

    面包店烹制面包及蛋糕,由n个销售员卖出.当有顾客进店购买面包或蛋糕时,应先在取号机上取号,然后等待叫号,若有销售员空闲时便叫下一号,试用信号量和PV操作写出Bakery算法的同步程序. 设计要求 1) ...

  8. 转 信号量与PV操作

    在计算机操作系统中,PV操作是进程管理中的难点.首先应弄清PV操作的含义:PV操作由P操作原语和V操作原语组成(原语是不可中断的过程),对信号量进行操作,具体定义如下:    P(S):①将信号量S的 ...

  9. 【转】进程同步之信号量机制(pv操作)及三个经典同步问题

    原文地址:http://blog.csdn.net/speedme/article/details/17597373 上篇博客中(进程同步之临界区域问题及Peterson算法),我们对临界区,临界资源 ...

  10. OS__信号量(semaphore)PV操作

    信号量的概念 1.信号量的类型定义 信号量(semaphore)的数据结构为记录型数据结构一个值和一个指针,指针指向等待该信号量的下一个进程.信号量的值与相应资源的使用情况有关,在操作系统中,信号量用 ...

随机推荐

  1. Linux C基础——” Makefile “ 文件管理大师你拜访过嘛?

    Make简介: 工程管理器,顾名思义,是指管理较多的文件 Make工程管理器也就是个"自动编译管理器",这里的"自动"是指它能够根据文件时间戳自动发现更新过的文 ...

  2. Webpack 核心流程

    我们是袋鼠云数栈 UED 团队,致力于打造优秀的一站式数据中台产品.我们始终保持工匠精神,探索前端道路,为社区积累并传播经验价值. 本文作者:霜序 三个阶段 初始化阶段 初始化参数:从配置文件.配置对 ...

  3. docker启动问题: Job for docker.service failed because the control process exited with error code. See "systemctl status docker.service" and "journalctl -xe" for details.

    系统环境:centos 7 docker版本:Docker version 26.1.4, build 5650f9b 问题:Job for docker.service failed because ...

  4. CTC联结时间分类算法: 连接主义时间分类: 用递归神经网络标记未分割序列数据《Connectionist Temporal Classification: Labelling Unsegmented Sequence Data with Recurrent Neural Networks》(语音、文本识别、RNN端到端训练序列数据的方法)

    11月6号例会汇报. 糊弄的看了一个算法-CTC算法,没有汇报论文,因为没看论文(我导知道后,应该会锤死我...) 当然,汇报完之后,被我导腾讯会议通过网线批了我一顿,PPT做的太烂了!字太多,听不到 ...

  5. java_day3_Scanner,顺序结构,选择结构(if,switch),循环结构(for,while),

    一.Scanner 键盘录入:程序运行过程中,用户可以根据自己的需求输入参与运算的值 实现键盘录入的步骤 1.导包 2.创建键盘录入对象 3.调用方法实现键盘录入 1)输入整数 2)输入字符串 pub ...

  6. MyBatis——案例——查询-多条件查询(多参数接收的三种方法)

    查询-多条件查询   编写接口方法:Mapper接口       参数:所有条件查询 List<Brand> selectByCondition(int status,String com ...

  7. HTML——简介-入门

    W3C标准:网页主要由三部分组成 结构:HTML 表现:CSS 行为:JavaScript HTML快速入门   1.新建文本文件,后缀改为 .html   2.编写HTML结构标签(不区分大小写) ...

  8. Codeforces Round 955 (Div. 2)

    A 非常好特判 一共就五种情况,相等,或者正反两种包含(都是不能可能不包含),或者正反两种先后(都是可能不相等),写五个 if 就行了 B 我到底为什么要跳了这题??????????????????? ...

  9. Windows系统无法打开‘’网络发现‘’功能

    Windows10无法开启网络发现 解决办法: 1. services.msc 2. 开启 SSDP Discovery ,设置 启动类型为 自动 ,服务状态为 启动 Windows7 无法开启网络发 ...

  10. 【赵渝强老师】使用Weblogic的WLST工具

    一.什么是Weblogic WLST? WebLogic 脚本工具 (WebLogic Scripting Tool , WLST) 是一种命令行脚本界面,系统管理员和操作员用它来监视和管理 WebL ...