线程同步的方法有哪几种_多线程的实现方式

线程同步的方法有哪几种_多线程的实现方式多线程之线程同步的四种方法1、互斥对象互斥对象包含一个使用数量,一个线程ID和一个计数器。它能确保线程拥有对单个资源的互斥访问权。1)创建互斥对象:调用函数CreateMutex

多线程之线程同步的四种方法   1、互斥对象   互斥对象包含一个使用数量,一个线程ID和一个计数器。它能确保线程拥有对单个资源的互斥访问权。   1)创建互斥对象:调用函数CreateMutex,返回值是句柄HANDLE。调用成功,该函数返回所创建的互斥对象的句柄。   2)请求互斥对象的所有权:调用函数WaitForSingleObject。处于阻塞状态,等待内核对象变为已通知状态。   3)释放指定互斥对象的所有权:调用函数ReleaseMutex。主动释放对互斥对象的所有权,使该对象处于已通知状态,线程才不会继续阻塞。   互斥对象函数CreateMutex的参数包括   首先,在全局定义一个互斥量的句柄变量以及全局变量num   在main中创建互斥对象,用hMutex来维护   在线程1函数中,在操作全局变量之前加上等待信号函数,并在操作完全局变量之后释放互斥对象   线程2函数同理   注意在main中最后关闭句柄   2、互斥事件   1)创建互斥事件:调用CreateEvent函数,返回值是句柄。创建一个匿名或命名的事件对象。   2)设置事件对象状态:调用SetEvent函数,把指定的事件对象设置为有信号状态。(有信号状态才会执行,否则就会处于等待状态)   3)重置事件对象状态:调用ResetEvent函数,把指定的事件对象设置为无信号状态。   4)请求事件对象:调用WaitForSingleObject函数,等待信号状态。   CreateEvent函数参数包括   案例:输入一个全局字符串:ABCD   通过多线程的方式来判断有几个字母A,必须用事件对象的方式来实现。   首先,定义一个全局的字符串数组和一个事件句柄。   在main中设置输入与读取函数   在main中创建互斥事件,用hEvent来维护   在全局定义两个线程函数,一个用来统计A的个数,一个用来统计非A的个数   在main中起两个线程,对应上方的功能   编写NumberOfAs和NumberOfOthers函数   直到两个线程都执行完毕之后,得到了A和非A的个数,再在main中将事件对象hEvent重置为无信号状态,并关闭句柄   3、信号量   信号量与互斥量不同的地方是,它允许多个线程在同一时刻访问同一资源,但是需要限制在同一时刻访问此资源的最大线程数目。信号量对象对线程的同步方式与前面几种方法不同,信号允许多个线程同时使用共享资源。   就好比一个停车场里有3个停车位,但外面有5辆车要进来,门卫这时候只允许其中3辆车进入,剩下2辆必须在门口等待。若有1辆车离开停车场,门卫才允许正在等待的其中1辆车进入,如此往复。在这个停车场中,每辆车代表1个线程,而门卫就是信号量,限制了可以活动的车辆(即线程)。此外,门卫也可以决定最多停几辆,比如有3个停车位,但门卫只允许停2个停车位,则只允许2辆车进入。   1)创建信号量:调用CreateSemaphoreW函数。其参数包括   2)增加信号量:调用ReleaseSamaphore函数。其参数包括   该函数用在操作完全局变量之后   信号量方法不常用,不展示案例   4、关键代码段   关键代码段,也称为临界区。   1)初始化关键代码段:调用InitialzeCriticalSection函数。该函数只有一个参数,在调用之前,首先需要构造一个CRITICAL_SECTION结构体类型的对象,同时该对象的地址就为该函数的参数。   2)进入关键代码段:调用EnterCriticalSection函数。以指定的临界区对象的所有权,也就是操作全局变量的那段代码,进入等待状态。   3)退出关键代码段:调用LeaveCriticalSection函数。在线程使用完临界区所保护的资源后,调用该函数,释放指定的临界区对象的所有权。之后,其它想要该临界区所有权的线程就可以获得该所有权,从而进入关键代码段,访问保护的资源。   4)删除关键代码段:调用DeleteCriticalSection函数。当临界区不再需要时,调用该函数释放该对象。   案例:卖票系统   有A、B两台售票机,现要售出5000张票,利用关键代码段的方式编写程序,使两台售票机共同将票售罄   首先在全局定义票数和结构体对象   在main中,定义两个句柄分别代表售票机A和B,并为它们创建线程,创建好后就关闭句柄   在main中,调用初始化函数,并设置延迟,规定在40s内卖完   开始编写A和B的售票逻辑,即SellTicketA和SellTicketB函数   逻辑是,在线程A中执行EnterCriticalSection,进入了关键代码段后,售票只会在该线程A中进行,而不会突然就转到B中售票,直到调用了LeaveCriticalSection函数,才会结束A的这一轮售票。后面可能是A接着新一轮售票,也可能轮到B售票,两者不定,如此往复,一轮接着一轮,实现了线程的同步。   卖完后,在main中删除临界区即可

2024最新激活全家桶教程,稳定运行到2099年,请移步至置顶文章:https://sigusoft.com/99576.html

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。 文章由激活谷谷主-小谷整理,转载请注明出处:https://sigusoft.com/58130.html

(0)
上一篇 2024年 8月 30日 下午9:47
下一篇 2024年 8月 30日

相关推荐

关注微信