当前位置: 首页 > news >正文

大型门户网站核心技术河南工程建设信息网站

大型门户网站核心技术,河南工程建设信息网站,域名解析到别人网站,wordpress 删除表前言 本文章主要介绍C11语法中std::thread的使用#xff0c;以及条件变量和互斥量的使用。 std::thread介绍 构造函数 std::thread 有4个构造函数 // 默认构造函#xff0c;构造一个线程对象#xff0c;在这个线程中不执行任何处理动作 thread() noexcept;// 移动构造函…前言 本文章主要介绍C11语法中std::thread的使用以及条件变量和互斥量的使用。 std::thread介绍 构造函数 std::thread 有4个构造函数 // 默认构造函构造一个线程对象在这个线程中不执行任何处理动作 thread() noexcept;// 移动构造函数。将 other 的线程所有权转移给新的thread 对象。之后 other 不再表示执行线程。 // 线程对象只可移动不可复制 thread( thread other ) noexcept;// 创建线程对象并在该线程中执行函数f中的业务逻辑args是要传递给函数f的参数 template class F, class... Args explicit thread( F f, Args... args );// 使用delete显示删除拷贝构造, 不允许线程对象之间的拷贝 thread( const thread ) delete;通过以下代码演示下如何构造函数的使用 #include iostream#include thread#include chronovoid threadFunc2() {std::cout enter threadFunc2 std::endl;}void threadFunc3(int data) {std::cout enter threadFunc3, data: data std::endl;}class CThread4 {public:void threadFunc4(const char * data) {std::cout enter threadFunc4, data: data std::endl;}};void threadFunc5() {for (int i 0; i 5; i) {std::cout enter threadFunc5 std::endl;std::this_thread::sleep_for(std::chrono::seconds(1));}}int main() {// 默认构造std::thread th1;// 线程中执行函数std::thread th2(threadFunc2);th2.join();// 线程中执行带参函数std::thread th3(threadFunc3, 10010);th3.join();CThread4 ct4;// 线程中执行类成员函数std::thread th4(CThread4::threadFunc4, ct4, hello world);th4.join();std::thread th5_1(threadFunc5);// 使用移动构造std::thread th5_2(std::move(th5_1));th5_2.join();// 执行lambda表达式std::thread th6([] {std::cout enter threadFunc6 std::endl;});th6.join();system(pause);return 0;}执行结果 enter threadFunc2enter threadFunc3, data: 10010enter threadFunc4, data: hello worldenter threadFunc5enter threadFunc5enter threadFunc5enter threadFunc5enter threadFunc5enter threadFunc6请按任意键继续. . .成员函数 // 获取线程ID std::thread::id get_id() const noexcept; // 阻塞当前线程直至调用join的子线程运行结束 void join(); // 将执行线程从线程对象中分离允许独立执行。 void detach(); // 判断主线程和子线程的关联状态 bool joinable() const noexcept; // 如果 *this 仍然有一个关联的运行中的线程则调用 std::terminate()。 // 否则将 other 的状态赋给 *this 并将 other 设置为默认构造的状态。 thread operator( thread other ) noexcept;通过代码看下如何使用成员函数 #include iostream#include thread#include chronovoid threadFunc3(int data) {std::cout enter threadFunc3, data: data std::endl;}void threadFunc4(int data) {std::cout start threadFunc4, data: data std::endl;std::this_thread::sleep_for(std::chrono::seconds(2));std::cout end threadFunc4, data: data std::endl;}void threadFunc5(int data) {std::cout start threadFunc5, data: data std::endl;std::this_thread::sleep_for(std::chrono::seconds(2));std::cout end threadFunc5, data: data std::endl;}int main() {{// 线程中执行带参函数std::thread th3(threadFunc3, 10010);std::cout th3 id: th3.get_id() std::endl;// 此刻th3线程与主线程有关联std::cout th3 joinable: th3.joinable() std::endl;th3.join();std::cout th3 id: th3.get_id() std::endl;// 线程执行结束此刻th3线程与主线程无关联std::cout th3 joinable: th3.joinable() std::endl;}{std::thread th5(threadFunc5, 10050);// 如果不想在主线程中等待子线程可以使用detach。// 这样即便主线程运行结束子线程依旧会执行// 实际使用时不建议这样做th5.detach();}system(pause);return 0;}执行结果 enter threadFunc3, data: 10010th3 id: 12820th3 joinable: 1th3 id: 0th3 joinable: 0start threadFunc5, data: 10050请按任意键继续. . . end threadFunc5, data: 10050条件变量 条件变量是C11提供的一种用于等待的同步机制它能阻塞一个或多个线程直到收到另外一个线程发出的通知或者超时时才会唤醒当前阻塞的线程。C11中的条件变量叫 condition_variable需要配合std::unique_lockstd::mutex使用。先看以下一段代码 #include iostream#include thread#include chrono#include mutex#include condition_variableint g_cnt 0;// 定义互斥量std::mutex g_mutex;// 定义条件变量std::condition_variable g_cond;void threadFunc1() {while (g_cnt ! 50) {std::this_thread::sleep_for(std::chrono::milliseconds(1));}std::cout threadFunc1 g_cnt: g_cnt std::endl;}void threadFunc2() {while (g_cnt 100) {g_cnt;std::this_thread::sleep_for(std::chrono::milliseconds(1));}}int main() {{std::thread th1(threadFunc1);std::thread th2(threadFunc2);th1.join();th2.join();std::cout g_cnt: g_cnt std::endl;}system(pause);return 0;}线程2对g_cnt进行递增操作线程1在g_cnt等于50时退出循环并打印结果。但这个流程有一个问题比如线程1某次访问g_cnt时值为49下一次再访问时值可能为50也可能为51。如果g_cnt值为51那这个条件永远都不会满足循环也就永远无法结束。并且线程1中我们只想获取g_cnt等于50这个状态没必要每次都去访问这也会耗费系统资源。使用条件变量做以下修改 #include iostream#include thread#include chrono#include mutex#include condition_variableint g_cnt 0;// 定义互斥量std::mutex g_mutex;// 定义条件变量std::condition_variable g_cond;bool g_flag false;void threadFunc1() {std::unique_lockstd::mutex lock(g_mutex);while (!g_flag) {// 阻塞等待,等待被唤醒g_cond.wait(lock);}std::cout threadFunc1 g_cnt: g_cnt std::endl;}void threadFunc2() {while (g_cnt 100) {g_cnt;if (g_cnt 50) {g_flag true;// 唤醒阻塞的线程g_cond.notify_one();}std::this_thread::sleep_for(std::chrono::milliseconds(1));}}int main() {{std::thread th1(threadFunc1);std::thread th2(threadFunc2);th1.join();th2.join();std::cout g_cnt: g_cnt std::endl;}system(pause);return 0;}这样就可以保证线程1的条件肯定可以满足。 线程互斥 控制线程对共享资源的访问。比如写文件时不能读文件读文件时不能写文件。C11提供了4种互斥锁 std::mutex独占的互斥锁不能递归使用。std::timed_mutex带超时的独占互斥锁不能递归使用。在获取互斥锁资源时增加了超时等待功能。std::recursive_mutex递归互斥锁不带超时功能。允许同一线程多次获得互斥锁。std::recursive_timed_mutex带超时的递归互斥锁。 分析以下这段代码的输出结果 #include iostream#include thread#include chrono#include mutexint g_cnt 0;void threadFunc(int num) {for (int i 0; i num; i) {g_cnt;std::this_thread::sleep_for(std::chrono::milliseconds(1));}}int main() {{// 线程中执行带参函数std::thread th1(threadFunc, 100);std::thread th2(threadFunc, 100);th1.join();th2.join();std::cout g_cnt: g_cnt std::endl;}system(pause);return 0;}我们期望的g_cnt输出结果为200但实际上g_cnt很大概率不是200而是小于200。这是由于没有对共享资源g_cnt进行加锁保护这会导致数据竞争。两个线程可能同时访问g_cnt导致某个线程的操作被另一个线程覆盖。对上面代码做下修改对共享资源g_cnt进行加锁保护。 #include iostream#include thread#include chrono#include mutexint g_cnt 0;// 定义互斥量std::mutex g_mutex;void threadFunc(int num) {for (int i 0; i num; i) {// 加锁g_mutex.lock();g_cnt;// 解锁g_mutex.unlock();std::this_thread::sleep_for(std::chrono::milliseconds(1));}}int main() {{// 线程中执行带参函数std::thread th1(threadFunc, 100);std::thread th2(threadFunc, 100);th1.join();th2.join();std::cout g_cnt: g_cnt std::endl;}system(pause);return 0;}加锁后就可以保证g_cnt的结果为200。上面代码有这样一种风险。如果加锁后中途退出而忘记解锁就会导致死锁现象。 void threadFunc(int num) {for (int i 0; i num; i) {// 加锁g_mutex.lock();g_cnt;if (i 50) {break;}// 解锁g_mutex.unlock();std::this_thread::sleep_for(std::chrono::milliseconds(1));}}C 11 提供了一种模板类 std::lock_guard可以简化互斥锁的写法。调用构造时加锁离开作用域时解锁。不用手动加解锁大大提高了安全性。实现代码如下。即便中途退出也不会出现死锁现象。 void threadFunc(int num) {for (int i 0; i num; i) {// 加锁std::lock_guardstd::mutex lock(g_mutex);g_cnt;if (i 50) {break;}std::this_thread::sleep_for(std::chrono::milliseconds(1));}}参考 https://en.cppreference.com/w/cpp/thread/thread
http://www.hkea.cn/news/14369009/

相关文章:

  • 江苏省医院网站建设管理规范重庆新闻发布会最新
  • 广州 建设 招聘信息网站正规的品牌网站建设服务
  • eclipse tomcat 网站开发怎么制作网站来赚钱
  • 红杭州网站建设个人网站收款
  • 网站精美排版代码做网站项目后台的
  • 爱站网挖掘工具wordpress 搬家 换域名
  • 开发一个企业网站报价微信营销成
  • 怎样建一个好的网站上海建设机械网站
  • 搜索引擎广告优化惠州seo代理计费
  • 科泉网站济南专业seo推广公司
  • 做网站主要栏目内做培训体系的网站
  • 免费做图素材网站广东建工集团
  • 织梦网站安装出现dir小程序加盟代理电话
  • 哪家做网站做的好东莞松山湖天气
  • 怎样做百度网站seo内容优化是什么意思
  • 外贸网站模板建设衡阳网站定制
  • 网站建设可上传视频的百度网站官网入口网址
  • 网站建设的步骤图片过程温州网站建设前十公司
  • ssr网站怎么做做微商网站的软文
  • 怎么编程一个网站山东平台网站建设企业
  • dede添加网站背景秦皇岛黄金海岸好玩吗
  • 做deal网站网页特效制作
  • 网站搜索优化技巧建设网站有什么特点特色
  • 阿里巴巴做网站接单几率网站做打鱼游戏挣钱吗
  • 聊天网站建设代做毕业设计找哪个网站
  • 天津网站优化哪家好鹤壁市城乡一体化示范区规划图
  • 旅游网站技术方案河南省建设工会网站
  • 互联网营销工具有哪些优化百度百科
  • 做正规小说网站外贸类网站建设
  • 鄂州市城市建设档案馆网站深圳ui设计师招聘