使用Win32 API实现生产者消费者线程同步
使用win32 API创建线程,创建信号量用于线程的同步
创建信号量
语法例如以下
HANDLE semophore;
semophore = CreateSemaphore(lpSemaphoreAttributes, lInitialCount, lMaximumCount, lpName);
CreateSemophore函数的原型例如以下:
HANDLE WINAPI CreateSemaphore(
_In_opt_ LPSECURITY_ATTRIBUTES lpSemaphoreAttributes,//属性
_In_ LONG lInitialCount,//初始值
_In_ LONG lMaximumCount,//最大值
_In_opt_ LPCTSTR lpName//信号量对象的名字
);
函数返回一个指向信号量对象的句柄,是一个HANDLE对象
wait操作和signal操作
使用结构通常是这种
while(true){
WaitForSingleObject(semophore,INFINITE);//wait操作
//临界区
ReleaseSemaphore(semophore,1,NULL);//signal操作
}
两个函数的原型例如以下:
DWORD WaitForSingleObject(
HANDLE hHandle,//句柄。能够指向信号量或者线程
DWORD dwMilliseconds//等待的毫秒数
);
BOOL ReleaseSemaphore(
HANDLE hSemaphore,//句柄,指向信号量
LONG lReleaseCount,//给信号量添加值,通常是1
LPLONG lpPreviousCount//保存信号量之前的值的变量的指针
);
创建线程
HANDLE producer;
//PRODUCER 线程运行这个函数
//pro_id 线程id
producer = CreateThread(NULL, 0, PRODUCER, NULL, 0, &pro_id);//创建线程
函数原型
HANDLE WINAPI CreateThread(
_In_opt_ LPSECURITY_ATTRIBUTES lpThreadAttributes,//指向线程属性结构体的指针
_In_ SIZE_T dwStackSize,//栈的初始化大小,0表示使用默认的大小
_In_ LPTHREAD_START_ROUTINE lpStartAddress,//起始地址,也就是线程函数的指针
_In_opt_ LPVOID lpParameter,//线程函数參数的指针
_In_ DWORD dwCreationFlags,//控制创建的标志位,0表示线程创建后马上运行,CREATE_SUSPENDED表示新建为suspended状态,直到 ResumeThread 被调用时才运行。STACK_SIZE_PARAM_IS_A_RESERVATION,由dwStackSize 參数指定初始的保留栈的大小。不指定的话,dwStackSize指定提交的大小
_Out_opt_ LPDWORD lpThreadId//线程id的指针
);
生产者消费者线程同步代码例如以下
#include<Windows.h>
#include<iostream> #define QUEUE_LENGTH 10 //缓冲区长度 HANDLE full_sem; //满信号量
HANDLE empty_sem; //空信号量 struct Msg
{
int i;
};//消息结构 Msg MsgQueue[QUEUE_LENGTH]; //缓冲区
int head = 0;//队列头
int tail = 0;//队列尾 DWORD WINAPI CONSUMER(LPVOID lpParameter){//消费者线程
for (int i = 0;;i++){ WaitForSingleObject(full_sem, INFINITE);//wait操作
//WaitForSingleObject(mutex, INFINITE);//多个消费者须要加相互排斥信号量
int val = MsgQueue[head].i;
head = (head + 1) % QUEUE_LENGTH;
//ReleaseSemaphore(mutex, 1, NULL);//signal操作
std::cout << "CONSUMER : "<<val<< std::endl; ReleaseSemaphore(empty_sem, 1, NULL);//signal操作
} return 0;
} DWORD WINAPI PRODUCER(LPVOID lpParameter){//生产者线程
for (int i = 0;; i++){
WaitForSingleObject(empty_sem, INFINITE);
//WaitForSingleObject(mutex, INFINITE);//多个生产者须要加相互排斥信号量
MsgQueue[tail].i = i;
tail=(tail+1) % QUEUE_LENGTH;
//ReleaseSemaphore(mutex, 1, NULL);
std::cout << "PRODUCER : " <<i<< std::endl; ReleaseSemaphore(full_sem, 1, NULL);
} return 0;
} int main(){ full_sem = CreateSemaphore(NULL, 0, QUEUE_LENGTH, NULL);//创建信号量 初始值为0,最大值为QUEUE_LENGTH
empty_sem = CreateSemaphore(NULL,QUEUE_LENGTH,QUEUE_LENGTH,NULL); DWORD pro_id;//pid
DWORD con_id; HANDLE producer = CreateThread(NULL, 0, PRODUCER, NULL, 0, &pro_id);//创建线程
//Sleep(1000);//展示堵塞 HANDLE consumer = CreateThread(NULL, 0, CONSUMER, NULL, 0, &con_id); WaitForSingleObject(producer, INFINITE);
WaitForSingleObject(consumer, INFINITE);//等待线程运行完成 CloseHandle(producer);
CloseHandle(consumer);//关闭内核对象 }
使用Win32 API实现生产者消费者线程同步的更多相关文章
- Hadoop生态圈-Kafka的旧API实现生产者-消费者
Hadoop生态圈-Kafka的旧API实现生产者-消费者 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.旧API实现生产者-消费者 1>.开启kafka集群 [yinz ...
- Java基础 线程的通信的三个方法/ 交替数数线程 / 生产者&消费者线程问题
线程通讯笔记: /** 线程通信 三个方法: * wait(): 调用该方法 是该调用的方法的线程释放共享资源的锁,进入等待状态,直至被唤醒 * notify() : 可以唤醒队列中的第一个等待同一共 ...
- [C++] socket - 6 [API互斥事件对象实现线程同步]
/*API互斥事件对象实现线程同步*/ #include<windows.h> #include<stdio.h> DWORD WINAPI myfun1(LPVOID lpP ...
- [C++] socket - 5 [API事件对象实现线程同步]
/*API事件对象实现线程同步*/ #include<windows.h> #include<stdio.h> DWORD WINAPI myfun1(LPVOID lpPar ...
- Hadoop生态圈-Kafka的新API实现生产者-消费者
Hadoop生态圈-Kafka的新API实现生产者-消费者 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任.
- wait和notify实现的生产者消费者线程交互
public class ProductTest { public static void main(String args[]) { Repertory repertory=new Repertor ...
- win32多线程 (二)线程同步之临界区 (critical sections)
所谓critical sections 意指一小块“用来处理一份被共享之资源”的程序代码.你可能必须在程序的许多地方处理这一块可共享的资源.所有这些程序代码可以被同一个critical sectio ...
- linux 信号量sem实现 生产者—消费者(线程间通信)
#include<pthread.h> #include<stdlib.h> #include<stdio.h> #include<unistd.h> ...
- 经典线程同步问题(生产者&消费者)--Java实现
生产者-消费者(producer-consumer)问题是一个著名的线程同步问题.它描述的是:有一群生产者线程在生产产品,并将这些产品提供给消费者线程去消费. 为使生产者与消费者之间能够并发执行,在两 ...
随机推荐
- Criteria 查询
Criteria.Criterion接口和Expression类组成,他支持在运行时动态生成查询语句. Criteria查询是Hibernate提供的一种查询方式 Hibernate检索方式: PO ...
- mysql下载和安装Windows服务
一.下载mysql:https://dev.mysql.com/downloads/mysql/,解压拷贝到D:\software\mysql-8.0.13-winx64 二.在D:\software ...
- csf 课件转化为wmv正常格式
1. 下载csf文件到本地:如下图 2.从下面百度网盘下载到本地: https://pan.baidu.com/s/1BBbgq n85a 3.安装并出现下面图标,点击打开 4. 运行如下图 5. ...
- json 新用
如果使用struts2的action,可以省去属性赋值的工夫. 但是假如你没有使用struts2,而且使用的是ajax请求,通过json来传递参数.那我下面所说的对你可能是一个很好的解脱,从此告别re ...
- nagios 安装pnp4nagios插件
Naigos install pnp4nagios 绘图插件 原文地址:http://www.cnblogs.com/caoguo/p/5022230.html [root@Cagios ~]# yu ...
- Sandbox 沙盒
In computer security, a sandbox is a security mechanism for separating running programs, usually in ...
- ubuntu下Fiddler抓包
参考 https://www.cnblogs.com/jcli/p/4474332.html https://www.jianshu.com/p/4505c732e378 1. 你要有个Mono环境, ...
- CAD绘制一个对齐标注(com接口VB语言)
主要用到函数说明: _DMxDrawX::DrawDimAligned 绘制一个对齐标注.详细说明如下: 参数 说明 DOUBLE dExtLine1PointX 第一条界线开始点X值 DOUBLE ...
- 在vue中通过js动态控制图片按比列缩放
1.html 通过外层的div来给img对应的class,隐藏的img是得到img图片请求回来时的原始尺寸.外层div是固定大小,因此,图片有两种情况去适应外部div的尺寸.一种是宽度大于高度的情况, ...
- C# 泛基
1 你有时候希望在父类规定一些行为,让子类无法修改,但是这些实现是依赖一个子类才能获取的值,你又不可能知道所有的子类 ,没办法替它在父类里面初始化,这时候就需要在父类里面定义一个每个子类一个的,但又是 ...