Win32下两种用于C++的线程同步类(下)

上一篇中我介绍了一种通过封闭Critical Section对象而方便的使用互斥锁的方式,文中所有的例子是两个线程对同一数据一读一写,因此需要让它们在这里互斥,不能同时访问。而在实际情况中可能会有更复杂的情况出现,就是多个线程访问同一数据,一部分是读,一部分是写。我们知道只有读-写或写-写同时进行时可能会出现问题,而读-读则可以同时进行,因为它们不会对数据进行修改,所以也有必要在C++中封装一种方便的允许读-读并发、读-写与写-写互斥的锁。要实现这种锁,使用临界区就很困难了,不如改用内核对象,这里我使用的是互斥量(Mutex)。

总体的结构与上一篇中的类似,都是写出一个对锁进行封装的基类,再写一个用于调用加、解锁函数的类,通过对第二个类的生命周期的管理实现加锁和解锁。这里涉及到两个新问题,一是加锁、解锁动作都有两种,一种是加/解读锁,一种是加/解写锁;二是为了允许读-读并发,这里只声明一个Mutex是不够的,必须要声明多个Mutex,而且有多少个Mutex就同时允许多少个读线程并发,之所以这么说,是因为我们要使用的API函数是WaitForMultipleObjects。

WaitForMultipleObjects函数的功能就是等待对象状态被设置,MSDN中对它的说明为:

Waits until one or all of the specified objects are in the signaled state or the time-out interval elapses.

这是个很好用的函数,我们可以用它来等待某个或某几个对象,并且允许设置超时时间,等待成功时与超时时返回的值是不同的。如果返回的值比WAIT_ABANDONED小则表示等待成功。“等待成功”对于不同类型的内核对象有不同的意义,例如对于进程或线程对象,等待成功就表示进程或线程执行结束了;对于互斥量对象,则表示此对象现在不被任何其他线程拥有,并且一旦等待成功,当前线程即拥有了此互斥量,其他线程则不能同时拥有,直接调用ReleaseMutex函数主动释放互斥量。

时间: 2024-10-28 22:53:48

Win32下两种用于C++的线程同步类(下)的相关文章

Win32下两种用于C++的线程同步类(上)

线程同步是多线程程序设计的核心内容,它的目的是正确处理多线程并发时的各种问题,例如线程的等待.多个线程访问同一数据时的互斥,防死锁等.Win32提供多种内核对象和手段用于线程同步,如互斥量.信号量.事件.临界区等.所不同的是,互斥量.信号量.事件都是Windows的内核对象,当程序对这些对象进行控制时会自动转换到核心态,而临界区本身不是内核对象,它是工作在用户态的.我们知道从用户态转换到核心态是需要以时间为代价的,所以如果能在用户态就简单解决的问题,就可以不必劳烦核心态了. 这里我要说的是两种用

浅谈.NET下的多线程和并行计算(四)线程同步基础 下

回顾一下上次,我们讨论了lock/AutoResetEvent/ManualResetEvent以及Semaphore.这些用于线程同 步的结构叫做同步基元.同步基元从类型上可以分为锁定/通知/联锁三种.lock显然锁定方式,而且是独 占锁定,也就是在锁释放之前不能由其它线程获得. Semaphore也是一种锁定,只不过不是独占锁,可以 指定多少个线程访问代码块.AutoResetEvent和ManualResetEvent当然就是通知方式了,前者在通行之后 自动重置,后者需要手动重置.我们还看

应用Linux下两种中文输入法

一个得心应手的汉字输入法可以节约大量的时间,从而大大地提高办公效率.由于红旗Linux 4.0桌面版内置了智能拼音.紫光输入法等大家熟悉的输入法,所以这里主要介绍在其它主流桌面Linux发行版本--Red Hat 8.0/9.0及Mandrake 9.1下安装使用高效输入法.下面就详细介绍两种中文输入法的安装使用. 紫光拼音输入法 紫光拼音输入法的Linux版本是一个遵循GPL协议的中文输入法(在GNOME虚拟终端中键入rfinput命令即可看到协议说明)见图1所示.紫光拼音Windows版本颇

iOS6中ARC 下两种释放对象的方法

  使用了 ARC 之后,无疑大大减少了程序员进行内存管理的压力.你再也不用写 release/autorelease 代码了,再也不用写dealloc 方法了.但这不等于程序员不需要内存管理.例如,你需要在 viewDidUnload 方法中对对象进行释放,以防当内存警告发生时,你没有内存可以回收.当然ARC 托管对象的释放方式与 MRC 是不同的.对于 ARC 托管对象,你必须用 ARC 特有的两种释放方式: [self setOjbect:nil]; 或者: self.object=nil

Linux下两种删除过期文件的方法详述

一.概述 在实际的C软件开发项目中,不同的软件会在不同的目录中生成文件,由于磁盘的存储空间有限,开发人员不得不考虑对目录下的过期文件进行删除.一般说来,有两种删除过期文件的方法,一种是在C程序中实现,一种是利用crontab实现.本文对这两种方法的具体实现进行详细的介绍. 为了便于说明,本文中的过期文件的后缀为.c,存放在/home/zhou/zhouzx/Test目录下,过期时间为1天. 二.在C程序中实现过期文件删除 在该方法中,我们要考虑的主要问题为: (1)要删除过期多久的文件?文件存放

两种方法助你找出win7下扫描仪在哪里

  1.第一种方法是直接在电脑桌面上建立一个快捷方式,这样更加方便寻找了,方法是:依次展开找到:C:WindowsSystem32wiaacmgr.exe,然后将wiaacmgr.exe右击选择发送到桌面快捷方式即可. 2.第二种方法是首先鼠标点击电脑桌面左下角的开始按钮,然后在开始菜单中选择"设备和打印机"选项; 3.然后就可以在设备和打印机界面中找到扫描仪或一体机了,就会看到开始开始扫描.扫描属性等选项了,如果是一体机,可双击打开,就可以看到扫描仪操作了.

win7系统下浏览器主页被金山毒霸导航劫持的两种解决方法

  一般情况下,win7操作系统自带有IE浏览器,用户可直接打开浏览器观看视频或搜索网页内容等等.有的时候会发生浏览器主页被劫持的现象,一位用户说win7 32位系统明明打开浏览器主页却变成毒霸导航的网址,为什么会出现这样的情况呢?主要原因就是你安装了金山毒霸,而毒霸的"新保护功能"把你的主页劫持了.接下去,本教程小编介绍两种解决方法,大家可以往下学习. 解决方法: 方法一.卸载金山毒霸,这个不用教了吧. 方法二. 1.在毒霸设置页面,安全保护设置-上网保护; 2.点击上网保护,取消安

Java创建线程的两种方式_java

前言 多线程是我们开发过程中经常遇到的,也是必不可少需要掌握的.当我们知道需要进行多线程开发时首先需要知道的自然是如何实现多线程,也就是我们应该如何创建线程. 在Java中创建线程和创建普通的类的对象操作是一样的,我们可以通过两种方式来创建线程: 1.继承Thread类,并重写run()方法. 2.实现Runnable接口,并实现run()方法. 方法一:继承Thread类 代码非常简单 首先重载一个构造函数,以便我们可以给线程命名. 重写run()方法. 这里我们先让线程输出线程名+start

多线程:C#线程同步lock,Monitor,Mutex,同步事件和等待句柄(下)

转自 http://www.cnblogs.com/freshman0216/archive/2008/08/07/1256919.html    前两篇简单介绍了线程同步lock,Monitor,同步事件EventWaitHandler,互斥体Mutex的基本用法,在此基础上,我们对它们用法进行比较,并给出什么时候需要锁什么时候不需要的几点建议.最后,介绍几个FCL中线程安全的类,集合类的锁定方式等,做为对线程同步系列的完善和补充.       1.几种同步方法的区别       lock和M