关于互斥量的基本概念:百度百科互斥量

推荐参考博客:秒杀多线程第七篇 经典线程同步 互斥量Mutex

注意:互斥量也是一个内核对象,它用来确保一个线程独占一个资源的访问。互斥量与关键段的行为非常相似,并且互斥量可以用于不同进程中的线程互斥访问资源                                                                                                          本文地址

主要用到2个函数:CreateMutex,ReleaseMutex:

 

CreateMutex

函数功能:创建互斥量(注意与事件Event的创建函数对比)

函数原型:

HANDLE CreateMutex(

LPSECURITY_ATTRIBUTESlpMutexAttributes,

BOOLbInitialOwner,    

LPCTSTRlpName

);

第一个参数:表示安全控制,一般直接传入NULL。

第二个参数:用来确定互斥量的初始拥有者。如果传入TRUE表示互斥量对象内部会记录创建它的线程的线程ID号并将递归计数设置为1,由于该线程ID非零,所以互斥量处于未触发状态。如果传入FALSE,那么互斥量对象内部的线程ID号将设置为NULL,递归计数设置为0,这意味互斥量不为任何线程占用,处于触发状态。

第三个参数:用来设置互斥量的名称,在多个进程中的线程就是通过名称来确保它们访问的是同一个互斥量。

返回值:成功则返回一个表示互斥量的句柄,失败返回NULL。

 

ReleaseMutex

功能:释放互斥量

函数原型:

BOOL ReleaseMutex (HANDLEhMutex)

函数说明:

访问互斥资源前应该要调用等待函数,结束访问时就要调用ReleaseMutex()来表示自己已经结束访问,其它线程可以开始访问了。

 

另外还有个函数OpenMutex 可以打开其它进程中创建的互斥量

 

注意:主线程不要忘了删除互斥量

 

下面从一个例子说明:假设有三个线程都需要使用打印机,我们可以使用互斥量来控制,这样就可以保证每次只有一个线程在使用打印机

 #include<string>
#include<iostream>
#include<process.h>
#include<windows.h>
using namespace std; //声明互斥量句柄
HANDLE hmu; //线程绑定的函数返回值和参数是确定的,而且一定要__stdcall
unsigned __stdcall threadFun(void *param)
{
WaitForSingleObject(hmu, INFINITE);//等待互斥量
cout<<*(string *)(param)<<endl;
ReleaseMutex(hmu);//释放互斥量
return 1;
} int main()
{
//创建互斥量
hmu = CreateMutex(NULL, FALSE, NULL); HANDLE hth1, hth2, hth3;
string s1 = "first", s2 = "second", s3 = "third"; //创建线程
hth1 = (HANDLE)_beginthreadex(NULL, 0, threadFun, &s1, 0, NULL);
hth2 = (HANDLE)_beginthreadex(NULL, 0, threadFun, &s2, 0, NULL);
hth3 = (HANDLE)_beginthreadex(NULL, 0, threadFun, &s3, 0, NULL); //等待子线程结束
WaitForSingleObject(hth1, INFINITE);
WaitForSingleObject(hth2, INFINITE);
WaitForSingleObject(hth3, INFINITE); //一定要记得关闭线程句柄
CloseHandle(hth1);
CloseHandle(hth2);
CloseHandle(hth3); //千万别忘了删除互斥量
CloseHandle(hmu);
}

 

互斥量有没有和临界区一样具有所有权属性呢,我们也从相同的例子来看:编写一个程序,开启3个线程,这3个线程的ID分别为A、B、C,每个线程将自己的ID在屏幕上打印10遍,要求输出结果必须按ABC的顺序显示;如:ABCABC….依次递推。

 #include<string>
#include<iostream>
#include<process.h>
#include<windows.h>
using namespace std;
//声明3个互斥量句柄
HANDLE hmu1, hmu2, hmu3; //线程绑定的函数返回值和参数是确定的,而且一定要__stdcall
unsigned __stdcall threadFunA(void *)
{
for(int i = 0; i < 10; i++){
WaitForSingleObject(hmu1, INFINITE);//等待互斥量
cout<<"A";
ReleaseMutex(hmu2);//释放互斥量
}
return 1;
}
unsigned __stdcall threadFunB(void *)
{
for(int i = 0; i < 10; i++){
WaitForSingleObject(hmu2, INFINITE);//等待互斥量
cout<<"B";
ReleaseMutex(hmu3);//释放互斥量
}
return 2;
}
unsigned __stdcall threadFunC(void *)
{
for(int i = 0; i < 10; i++){
WaitForSingleObject(hmu3, INFINITE);//等待互斥量
cout<<"C";
ReleaseMutex(hmu1);//释放互斥量
}
return 3;
} int main()
{
hmu1 = CreateMutex(NULL, FALSE, NULL);
hmu2 = CreateMutex(NULL, FALSE, NULL);
hmu3 = CreateMutex(NULL, FALSE, NULL); HANDLE hth1, hth2, hth3;
//创建线程
hth1 = (HANDLE)_beginthreadex(NULL, 0, threadFunA, NULL, 0, NULL);
hth2 = (HANDLE)_beginthreadex(NULL, 0, threadFunB, NULL, 0, NULL);
hth3 = (HANDLE)_beginthreadex(NULL, 0, threadFunC, NULL, 0, NULL); //等待子线程结束
WaitForSingleObject(hth1, INFINITE);
WaitForSingleObject(hth2, INFINITE);
WaitForSingleObject(hth3, INFINITE); //一定要记得关闭线程句柄
CloseHandle(hth1);
CloseHandle(hth2);
CloseHandle(hth3); //删除互斥量
CloseHandle(hmu1);
CloseHandle(hmu2);
CloseHandle(hmu3);
}

 

从结果看互斥量也具有所有权属性,即拥有互斥量的线程可以重复进入互斥量保护的区域

 

【版权声明】转载请注明出处http://www.cnblogs.com/TenosDoIt/p/3601387.html

windows多线程同步--互斥量的更多相关文章

  1. 总结windows多线程同步互斥

    windows多线程同步互斥--总结 我的windows多线程系列文章: windows多线程--原子操作 windows多线程同步--事件 windows多线程同步--互斥量 windows多线程同 ...

  2. windows多线程同步互斥--总结

    我的windows多线程系列文章: windows多线程--原子操作 windows多线程同步--事件 windows多线程同步--互斥量 windows多线程同步--临界区 windows多线程同步 ...

  3. 多线程面试题系列(7):经典线程同步 互斥量Mutex

    前面介绍了关键段CS.事件Event在经典线程同步问题中的使用.本篇介绍用互斥量Mutex来解决这个问题. 互斥量也是一个内核对象,它用来确保一个线程独占一个资源的访问.互斥量与关键段的行为非常相似, ...

  4. 秒杀多线程第七篇 经典线程同步 互斥量Mutex

    本文转载于:http://blog.csdn.net/morewindows/article/details/7470936 前面介绍了关键段CS.事件Event在经典线程同步问题中的使用.本篇介绍用 ...

  5. 转--- 秒杀多线程第七篇 经典线程同步 互斥量Mutex

    阅读本篇之前推荐阅读以下姊妹篇: <秒杀多线程第四篇一个经典的多线程同步问题> <秒杀多线程第五篇经典线程同步关键段CS> <秒杀多线程第六篇经典线程同步事件Event& ...

  6. 经典线程同步 互斥量Mutex

    阅读本篇之前推荐阅读以下姊妹篇: <秒杀多线程第四篇一个经典的多线程同步问题> <秒杀多线程第五篇经典线程同步关键段CS> <秒杀多线程第六篇经典线程同步事件Event& ...

  7. (转)经典线程同步 互斥量Mutex

    阅读本篇之前推荐阅读以下姊妹篇: <秒杀多线程第四篇一个经典的多线程同步问题> <秒杀多线程第五篇经典线程同步关键段CS> <秒杀多线程第六篇经典线程同步事件Event& ...

  8. windows多线程同步--临界区

    推荐参考博客:秒杀多线程第五篇 经典线程同步 关键段CS   关于临界区的观念,一般操作系统书上面都有. 适用范围:它只能同步一个进程中的线程,不能跨进程同步.一般用它来做单个进程内的代码快同步,效率 ...

  9. Linux多线程——使用互斥量同步线程

    前文再续,书接上一回,在上一篇文章: Linux多线程——使用信号量同步线程中,我们留下了一个如何使用互斥量来进行线程同步的问题,本文将会给出互斥量的详细解说,并用一个互斥量解决上一篇文章中,要使用两 ...

随机推荐

  1. python 全栈开发,Day33(tcp协议和udp协议,互联网协议与osi模型,socket概念,套接字(socket)初使用)

    先来回顾一下昨天的内容 网络编程开发架构 B/S C/S架构网卡 mac地址网段 ip地址 : 表示了一台电脑在网络中的位置 子网掩码 : ip和子网掩码按位与得到网段 网关ip : 内置在路由器中的 ...

  2. VS-常用的快捷键-总结

    1: 快速添加引用 === Shift+Alt+F10; 也可用于实现抽象类 2: 直接添加属性 ===prop+Tab+Tab; 3: 根据字段添加属性 === Ctrl +r+e; 4: 格式化代 ...

  3. Zookeeper笔记(三)部署与启动Zookeeper

    下载zookeeper安装包 去Zookeeper官网,下载地址http://zookeeper.apache.org/releases.html,建议下载稳定版本,我下载的是zookeeper-3. ...

  4. openstack时间不同步问题

    一.出现的问题 我们在安装openstack的时候如果没有设置计算节点和控制节点的的时间同步,当你虚拟机开机之后会存在控制节点和计算节点的时间 不一样,导致opstack无法登陆,报如下错误: 二.设 ...

  5. 异常Cannot get a text value from a numeric cell

    POI操作Excel时偶尔会出现Cannot get a text value from a numeric cell的异常错误. 异常原因:Excel数据Cell有不同的类型,当我们试图从一个数字类 ...

  6. python全栈开发day50-jquery之ajax、XmlHttpRquest

    一.昨日内容回顾 1.jquery位置信息 width() ..,innetWidth() .outWidth() offset().top left scrollTop 2.事件流 DOM2级 (1 ...

  7. django引入现有数据库

    Django引入外部数据库还是比较方便的,步骤如下: 1.创建一个项目,修改seting文件,在setting里面设置你要连接的数据库类型和连接名称,地址之类,和创建新项目的时候一致. 2.运行下面代 ...

  8. java作业第三次作业

    (一)作业总结 1.阅读下面程序,分析是否能编译通过?如果不能,说明原因.应该如何修改?程序的运行结果是什么? 为什么子类的构造方法在运行之前,必须调用父 类的构造方法?能不能反过来? class G ...

  9. POJ 1228 (稳定凸包问题)

    <题目链接> <转载于  >>> > 首先来了解什么是稳定的凸包.比如有4个点: 这四个点是某个凸包上的部分点,他们连起来后确实还是一个凸包.但是原始的凸包可 ...

  10. 中间人攻击工具mitmf(另类的XSS注入攻击)

    中间人攻击工具mitmf(另类的XSS注入攻击) (一)简介 (二)安装 (三)结合beef使用 (一)简介 Mitmf 是一款用来进行中间人攻击的工具.它可以结合 beef 一起来使用,并利用 be ...