Cocos2d-X多线程(2) 线程的互斥量std::mutex和线程锁
多个线程同时访问共享资源时,经常会出现冲突等。为了避免这种情况的发生,可以使用互斥量,当一个线程锁住了互斥量后,其他线程必须等待这个互斥量解锁后才能访问它。
thread提供了四种不同的互斥量:
1、独占式互斥量non-recursive (std::mutex)
独占式互斥量加解锁是成对的,同一个线程内独占式互斥量在没有解锁的情况下,再次对它进行加锁这是不对的,会得到一个未定义行为。
2、递归式互斥量recursive (std::recursive_mutex)
与独占式互斥量不同的是,同一个线程内在互斥量没有解锁的情况下可以再次进行加锁,不过他们的加解锁次数需要一致,递归式互斥量我们平时可能用得比较少些。
3、允许超时的独占式互斥量non-recursive that allows timeouts on the lock functions(std::timed_mutex)
用法同独占式互斥量,如果线程1对共享资源的访问时间比较长,这时线程2可能等不了那么久,所以设置一个超时时间,在到了超时时间时如果线程1中的互斥量还没有解锁,线程2就不等了,继续往下执行。
4、允许超时的递归式互斥量recursive mutex that allows timeouts on the lock functions (std::recursive_timed_mutex)
下面以外卖为例演示下互斥量和线程锁的用法:假如有50份蛋炒饭,两个下单窗口同时运作,蛋炒饭卖完为止。
代码实操:
头文件:
#ifndef __TestMutex_SCENE_H__
#define __TestMutex_SCENE_H__
#include "cocos2d.h"
USING_NS_CC;
class TestMutex : public cocos2d::Layer
{
int total;//总量
int selled;//卖出量
public:
static cocos2d::Scene* createScene();
virtual bool init();
CREATE_FUNC(TestMutex);
void threadA();
void threadB();
};
#endif // __TestMutex_SCENE_H__
源文件:
#include "TestMutex.h"
#include <thread>
std::mutex _mutex;
Scene* TestMutex::createScene()
{
auto scene = Scene::create();
auto layer = TestMutex::create();
scene->addChild(layer);
return scene;
}
bool TestMutex::init()
{
if ( !Layer::init() )
{
return false;
}
total = 50;
selled = 0;
std::thread t1(&TestMutex::threadA,this);
t1.detach();
std::thread t2(&TestMutex::threadB,this);
t2.detach();
return true;
}
void TestMutex::threadA()
{
while (selled<total)
{
// 加锁
_mutex.lock();
selled++;
std::this_thread::sleep_for(std::chrono::seconds(3));
log("threadA %d",selled);
// 解锁
_mutex.unlock();
}
}
void TestMutex::threadB()
{
while (selled<total)
{
_mutex.lock();
selled++;
std::this_thread::sleep_for(std::chrono::seconds(3));
log("threadB %d",selled);
_mutex.unlock();
}
}
Cocos2d-X多线程(2) 线程的互斥量std::mutex和线程锁的更多相关文章
- pThreads线程(二) 线程同步--互斥量/锁
互斥量(Mutex)是“mutual exclusion”的缩写.互斥量是实现线程同步,和保护同时写共享数据的主要方法. 互斥量对共享数据的保护就像一把锁.在Pthreads中,任何时候仅有一个线程可 ...
- c++11 线程的互斥量
c++11 线程的互斥量 为什么需要互斥量 在多任务操作系统中,同时运行的多个任务可能都需要使用同一种资源.这个过程有点类似于,公司部门里,我在使用着打印机打印东西的同时(还没有打印完),别人刚好也在 ...
- 多线程面试题系列(7):经典线程同步 互斥量Mutex
前面介绍了关键段CS.事件Event在经典线程同步问题中的使用.本篇介绍用互斥量Mutex来解决这个问题. 互斥量也是一个内核对象,它用来确保一个线程独占一个资源的访问.互斥量与关键段的行为非常相似, ...
- 秒杀多线程第七篇 经典线程同步 互斥量Mutex
本文转载于:http://blog.csdn.net/morewindows/article/details/7470936 前面介绍了关键段CS.事件Event在经典线程同步问题中的使用.本篇介绍用 ...
- 转--- 秒杀多线程第七篇 经典线程同步 互斥量Mutex
阅读本篇之前推荐阅读以下姊妹篇: <秒杀多线程第四篇一个经典的多线程同步问题> <秒杀多线程第五篇经典线程同步关键段CS> <秒杀多线程第六篇经典线程同步事件Event& ...
- 经典线程同步 互斥量Mutex
阅读本篇之前推荐阅读以下姊妹篇: <秒杀多线程第四篇一个经典的多线程同步问题> <秒杀多线程第五篇经典线程同步关键段CS> <秒杀多线程第六篇经典线程同步事件Event& ...
- (转)经典线程同步 互斥量Mutex
阅读本篇之前推荐阅读以下姊妹篇: <秒杀多线程第四篇一个经典的多线程同步问题> <秒杀多线程第五篇经典线程同步关键段CS> <秒杀多线程第六篇经典线程同步事件Event& ...
- windows多线程(五) 互斥量 Mutex
一.互斥量 互斥量是windows的一个内核对象,互斥量与关键段的作用相似,可以用来确保全局资源的互斥访问.并且互斥量可以用在不同的进程中的线程互斥访问全局资源. 二.相关函数说明 使用互斥量Mute ...
- 生产者-消费者问题:介绍POSIX线程的互斥量和条件变量的使用
全局初始化互斥量和条件变量(不全局也行,但至少要对线程启动函数可见,这样才能使用.) static pthread_cont_t cond = PTHREAD_COND_INITIALIZER; st ...
随机推荐
- k8spod生命周期
pod对象自从创建开始至终止退出的时间范围称为生命周期,在这段时间中,pod会处于多种不同的状态,并执行一些操作:其中,创建主容器为必须的操作,其他可选的操作还包括运行初始化容器(init conta ...
- linux学习:【第2篇】之常见命令
linux之常见命令 创建一个目录 /data mkdir /data ls -l /data/ cd /data/ pwd 相对路径与绝对路径 1.绝对路径 从根开始的路径 /data 2.相对路径 ...
- cordova打包项目下载gradle失败
在使用cordova打包项目的时候有时会因为网络环境原因导致下载gradle失败的情况,个人找到两种解决方案. 方案一: 根据报错的提示选择要下载的gradle去浏览器中下载,然后将gradle压缩包 ...
- ASP.NET上传断点续传
IE的自带下载功能中没有断点续传功能,要实现断点续传功能,需要用到HTTP协议中鲜为人知的几个响应头和请求头. 一. 两个必要响应头Accept-Ranges.ETag 客户端每次提交下载请求时,服务 ...
- codevs 1405 牛的旅行x
牛的旅行 [问题描述] 农民John的农场里有很多牧区.有的路径连接一些特定的牧区.一片所有连通的牧区称为一个牧场.但是就目前而言,你能看到至少有两个牧场不连通.现在,John想在农场里添加一条路径 ...
- MySQL数据库入门———常用基础命令
mysql 连接数据库命令: MySQL 连接本地数据库,用户名为“root”,密码“123”(注意:“-p”和“123” 之间不能有空格) mysql -h localhost -u root -p ...
- js模拟24小时的倒计时效果
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title> ...
- python学习之路(3)
字符串和编码 因为python最早只支持ASCII编码普通的字符串'ABC'在Python内部都是ASCII编码的.Python提供了ord()和chr()函数,可以把字母和对应的数字相互转换 后来p ...
- Java Optional orElse() 和 orElseGet() Optional.flatMap()和Optional.map()区别
Java Optional 的 orElse() 和 orElseGet() 的区别 1. 接收的参数不同 orElse()方法以一个自定义类型的数据作为参数 public T orElse(T t) ...
- 从零开始学习vue(2)
一.vue实例 每个vue应用都是通过Vue构造函数创建的一个新的实例开始的: var vm = new Vue({ //选项对象 }) 在这其中vm(viewModel的简称)通常都表示vue实例的 ...