多线程PV
#include <STDIO.H>
#include <windows.h>
//#include "stdafx.h"
#include <process.h> // _beginthread && _endthread
//#include "BaseOperation.h"
#define N 10 typedef int semaphore; /* 信号量是一种特殊的整型变量 */ semaphore mutex=; /* 互斥访问 */
semaphore empty=N; /* 记录缓冲池中空的缓冲区数 */
semaphore full=; /* 记录缓冲池中满的缓冲区数*/ semaphore buf[N]; /* 有N个缓冲区数的缓冲池buf[N],并实现循环缓冲队列 */
semaphore in=, out=; void p(semaphore *x) /* p操作 */
{
*x=(*x)-;
} void v(semaphore *y) /* v操作 */
{
*y=(*y)+;
} void produce_item(int *item_ptr)
{
/*printf("produce an item\n");*/
*item_ptr='F'; /* 'F' is "Full满" */
} void enter_item(int x)
{
in=(out+)%N;
buf[in]=x;
printf("enter_item %c to buf[%d]\n", buf[in], in);
} void remove_item(int *yy)
{
out=(out+)%N;
printf("remove_item %c from buf[%d]", buf[out], out);
*yy=buf[out];
buf[out]='E'; /* 'E' is "Empty空" */
printf(" so the buf[%d] changed to empty--%c\n", out, buf[out]);
}
void consume_item(int y)
{
printf("cosume the item :the screem print %c\n", y);
} void producer(void);
void consumer(void);
int item;
DWORD WINAPI ThreadProc1( LPVOID lpParam )
{ int i=,j=;
while()
{
produce_item(&item); //延时
for(i=;i<;i++)
{
;
}
}
}
/* 生产者 */ DWORD WINAPI ThreadProc2( LPVOID lpParam )
{ int i=,j=;
while()
{
consumer(); //延时
for(i=;i<;i++)
{
;
}
}
} void producer(void)
{ while(){
//_beginthread(produce_item(&item),0,NULL);
CreateThread(
NULL, // default security attributes
, // use default stack size
ThreadProc1, // thread function
NULL, // argument to thread function
, // use default creation flags
NULL); // returns the thread identifier
p(&empty); /* 递减空缓冲区数 */
p(&mutex); /* 进入临界区 */
enter_item(item); /* 将一个新的数据项放入缓冲池 */
v(&mutex); /* 离开临界区 */
v(&full); /* 递增满缓冲区数 */
if(full==N) /* 若缓冲池满的话,唤醒消费者进程 */
CreateThread(
NULL, // default security attributes
, // use default stack size
ThreadProc2, // thread function
NULL, // argument to thread function
, // use default creation flags
NULL); // returns the thread identifier
}
} /* 消费者 */
void consumer(void)
{
int get_item; while(){
p(&full); /* 递减满缓冲区数 */
p(&mutex); /* 进入临界区 */
remove_item(&get_item); /* 从缓冲池中取走一个数据项 */
v(&mutex); /* 离开临界区 */
v(&empty); /* 递增空缓冲区数 */
consume_item(get_item); /* 对数据项进行操作(消费)*/
if(empty==N) /* 若缓冲池全空的话,唤生产者进程 */
producer();
}
} /* 调用生产者-消费者进程实现进程间同步 */
main()
{
producer(); return ;
}
#include <STDIO.H>
#include <windows.h>
//#include "stdafx.h"
#include <process.h> // _beginthread && _endthread
//#include "BaseOperation.h"
#define N 10 typedef int semaphore; /* 信号量是一种特殊的整型变量 */ semaphore mutex=; /* 互斥访问 */
semaphore empty=N; /* 记录缓冲池中空的缓冲区数 */
semaphore full=; /* 记录缓冲池中满的缓冲区数*/ semaphore buf[N]; /* 有N个缓冲区数的缓冲池buf[N],并实现循环缓冲队列 */
semaphore in=, out=; void p(semaphore *x) /* p操作 */
{
*x=(*x)-;
} void v(semaphore *y) /* v操作 */
{
*y=(*y)+;
} void produce_item(int *item_ptr)
{
/*printf("produce an item\n");*/
*item_ptr='F'; /* 'F' is "Full满" */
} void enter_item(int x)
{
in=(out+)%N;
buf[in]=x;
printf("enter_item %c to buf[%d]\n", buf[in], in);
} void remove_item(int *yy)
{
out=(out+)%N;
printf("remove_item %c from buf[%d]", buf[out], out);
*yy=buf[out];
buf[out]='E'; /* 'E' is "Empty空" */
printf(" so the buf[%d] changed to empty--%c\n", out, buf[out]);
}
void consume_item(int y)
{
printf("cosume the item :the screem print %c\n", y);
} void producer(void);
void consumer(void);
int item;
DWORD WINAPI ThreadProc1( LPVOID lpParam )
{ int i=,j=;
while()
{
produce_item(&item); //延时
Sleep();
}
}
/* 生产者 */ DWORD WINAPI ThreadProc2( LPVOID lpParam )
{ int i=,j=;
while()
{
consumer(); //延时
Sleep();
}
} void producer(void)
{ while(){
//_beginthread(produce_item(&item),0,NULL);
CreateThread(
NULL, // default security attributes
, // use default stack size
ThreadProc1, // thread function
NULL, // argument to thread function
, // use default creation flags
NULL); // returns the thread identifier
p(&empty); /* 递减空缓冲区数 */
p(&mutex); /* 进入临界区 */
enter_item(item); /* 将一个新的数据项放入缓冲池 */
v(&mutex); /* 离开临界区 */
v(&full); /* 递增满缓冲区数 */
if(full==N) /* 若缓冲池满的话,唤醒消费者进程 */
CreateThread(
NULL, // default security attributes
, // use default stack size
ThreadProc2, // thread function
NULL, // argument to thread function
, // use default creation flags
NULL); // returns the thread identifier
}
} /* 消费者 */
void consumer(void)
{
int get_item; while(){
p(&full); /* 递减满缓冲区数 */
p(&mutex); /* 进入临界区 */
remove_item(&get_item); /* 从缓冲池中取走一个数据项 */
v(&mutex); /* 离开临界区 */
v(&empty); /* 递增空缓冲区数 */
consume_item(get_item); /* 对数据项进行操作(消费)*/
if(empty==N) /* 若缓冲池全空的话,唤生产者进程 */
producer();
}
} /* 调用生产者-消费者进程实现进程间同步 */
main()
{
producer(); return ;
}
多线程PV的更多相关文章
- 多线程同步内功心法——PV操作上(未完待续。。。)
阅读本篇之前推荐阅读以下姊妹篇: <秒杀多线程第四篇一个经典的多线程同步问题> <秒杀多线程第五篇经典线程同步关键段CS> <秒杀多线程第六篇经典线程同步事件Event& ...
- Java入门到精通——基础篇之多线程实现简单的PV操作的进程同步
Java入门到精通——基础篇之多线程实现简单的PV操作的进程同步 一.概述 PV操作是对信号量进行的操作. 进程同步是指在并发进程之间存在一种制约关系,一个进程的执行依赖另一个进程的消 ...
- 多线程面试题系列(12):多线程同步内功心法——PV操作上
上面的文章讲解了在Windows系统下实现多线程同步互斥的方法,为了提高在实际问题中分析和思考多个线程之间同步互斥问题的能力,接下来将讲解PV操作,这也是操作系统中的重点和难点.本文将会先简要介绍下P ...
- Java—多线程实现PV效果
前言 还记得今年参加自学操作系统考试,最难分析的就是PV这部分,然而伟大的米老师却用一个放东西吃东西的小例子,把PV讲的栩栩如生,言简意赅.学J2SE时学到了线程部分,里面提到了线程同步,死锁问题等等 ...
- windows多线程(九) PV原语分析同步问题
一.PV原语介绍 PV原语通过操作信号量来处理进程间的同步与互斥的问题.其核心就是一段不可分割不可中断的程序. 信号量的概念1965年由著名的荷兰计算机科学家Dijkstra提出,其基本思路是用一种新 ...
- 转---秒杀多线程第十二篇 多线程同步内功心法——PV操作上 (续)
PV操作的核心就是 PV操作可以同时起到同步与互斥的作用. 1.同步就是通过P操作获取信号量,V操作释放信号量来进行. 2.互斥其实就是,同时操作P操作,结束后进行V操作即可做到. Java上实现PV ...
- [多线程同步练习]PV操作
看一个较为复杂的生产者-消费者问题: 问题描述 桌子上有一只盘子,每次只能向其中放入一个水果.爸爸专向盘子中放苹果,妈妈专向盘子中放橘子,儿子专等吃盘子中的橘子,女儿专等吃盘子中的苹果.只有盘子为空时 ...
- iOS GCD NSOperation NSThread等多线程各种举例详解(拷贝)
2年多的iOS之路匆匆而过,期间也拜读来不少大神的博客,近来突然为自己一直做伸手党感到羞耻,是时候回馈社会.回想当年自己还是小白的时候,照着一些iOS多线程教程学,也只是照抄,只知其然.不知其所以然. ...
- 【五子棋AI循序渐进】——多线程搜索
关于多线程搜索,有很多方法来实现,很多文章推荐基于MTD(F)的方式.好处不言而喻,不过我的程序中采用的是基于PVS的多线程搜索.实现起来主要是这几个方面问题需要解决: 1.置换表的互斥访问. 2.局 ...
随机推荐
- Hadoop分布式集群搭建_1
Hadoop是一个开源的分布式系统框架 一.集群准备 1. 三台虚拟机,操作系统Centos7,三台主机名分别为k1,k2,k3,NAT模式 2.节点分布 k1: NameNode DataNode ...
- Python学习 :多线程 --- 锁
多线程 什么是锁? - 锁通常被用来实现对共享资源的同步访问. - 为每一个共享资源创建一个Lock对象,当你需要访问该资源时,调用acquire方法来获取锁对象(如果其它线程已经获得了该锁,则当前线 ...
- 总结2018&&展望2019
2019很激动,因为我加入了博客园这个大家庭,以后的技术文章都会在博客园记录,也希望可以结识更多的有趣朋友和共同理想的友人.第一篇文章从自我规划开始.2019 您好!!! 总结2018: 距离2018 ...
- Asp.Net Core存储Cookie不成功
Asp.Net Core存储Cookie不成功 Asp.Net Core2.1生成的项目模板默认实现了<>,所以设置存储Cookie需要做一些处理. 1.第一种是在Startup的Conf ...
- ACM--移动桌子--贪心--HDOJ 1050--Moving Tables
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others) Problem Descript ...
- 关于Oracle分区表的理解
Oracle分区表首要目的是用于管理数据文件,对数据文件进行划分和管理.但常常会听到通过分区表来提高性能的说法,实际上,分区表结合索引,加上有效的SQL语句,确实可以提高性能.什么是有效的SQL呢,就 ...
- 20145226夏艺华 网络对抗技术EXP8 WEB基础实践
20145226夏艺华 网络对抗技术EXP8 WEB基础实践 实验问题回答 1.什么是表单? 表单在网页中主要负责数据采集功能.一个表单有三个基本组成部分: 表单标签:这里面包含了处理表单数据所用CG ...
- [BZOJ3218]a + b Problem-[主席树+网络流-最小割]
Description 传送门 Solution 此处我们按最小割的思路考虑. 暴力:S->i表示该点选黑色的权值b[i]:i->T表示该点选白色的权值w[i].考虑如果某个点i受点j为白 ...
- 【信息安全】MD5加密浅析
前段时间,网传京东泄露了几G的用户数据,后面又说用户数据是MD5加密的,让大家不要担心,改个密码之类云云. 出于好奇,上网了解了一下这个MD5. 一.MD5加密方式是什么 简单讲,MD5加密是一个用到 ...
- c++ 自定义数据结构运用
教学内容: 定义结构 定义结构变量 访问结构成员 定义结构数组 实例运用 例:记录学生到校时间(精确到秒) struct mytime { int hour;//时 int min;//分 ...