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

网站怎样做关键词优化帝国视频网站模板

网站怎样做关键词优化,帝国视频网站模板,网站建设销售秘籍,wordpress seo 固定连接前言 本文章主要介绍C11语法中std::thread的使用,以及条件变量和互斥量的使用。 std::thread介绍 构造函数 std::thread 有4个构造函数 // 默认构造函,构造一个线程对象,在这个线程中不执行任何处理动作 thread() noexcept;// 移动构造函…

前言

  • 本文章主要介绍C++11语法中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 <chrono>void 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 <chrono>void 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
      

条件变量

  • 条件变量是C++11提供的一种用于等待的同步机制,它能阻塞一个或多个线程,直到收到另外一个线程发出的通知或者超时时,才会唤醒当前阻塞的线程。
  • C++11中的条件变量叫 condition_variable,需要配合std::unique_lock<std::mutex>使用。
  • 先看以下一段代码
    •   #include <iostream>#include <thread>#include <chrono>#include <mutex>#include <condition_variable>int 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_variable>int g_cnt = 0;// 定义互斥量std::mutex g_mutex;// 定义条件变量std::condition_variable g_cond;bool g_flag = false;void threadFunc1() {std::unique_lock<std::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的条件肯定可以满足。

线程互斥

  • 控制线程对共享资源的访问。比如写文件时,不能读文件,读文件时,不能写文件。
  • C++11提供了4种互斥锁
    • std::mutex:独占的互斥锁,不能递归使用。
    • std::timed_mutex:带超时的独占互斥锁,不能递归使用。在获取互斥锁资源时增加了超时等待功能。
    • std::recursive_mutex:递归互斥锁,不带超时功能。允许同一线程多次获得互斥锁。
    • std::recursive_timed_mutex:带超时的递归互斥锁。
  • 分析以下这段代码的输出结果
    •   #include <iostream>#include <thread>#include <chrono>#include <mutex>int 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 <mutex>int 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_guard<std::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.yayakq.cn/news/677992/

相关文章:

  • 哪里有免费的网站模板word+没有安装wordpress
  • 自己 做网站学什么 平面设计如何做招生网站
  • 广州市口碑好的网站制作排名熊猫办公ppt模板下载免费
  • php旅游网站开发小结个人网站备案名
  • 网站的外链怎么做厦门建设局网站城市建设
  • 专业网站制作价格全国通网站建设
  • 张家港英文网站制作小程序开发入门教程
  • 国内优秀的网站金融公司网站 html
  • 邢台营销型网站制作网络竞价推广开户
  • 企业网站建设cms系统移动应用开发学什么
  • 网站怎么优化 优帮云早厦门构网站建设
  • 做网站云服务器装系统新网站如何做sem
  • 四川电脑网站建设软件设计学什么课程
  • 三合一网站管理系统怎么做的建立收费网站
  • wordpress的网站怎样添加地图坐标wordpress 导航固定
  • 网站建设企业网站建设网站问题有哪些内容
  • 怎么查看网站用的php还是.net常州外贸网站建设公司
  • 网站的首页文案乐清企业网站建设
  • 诸城网站做的好的郑州市网络设计
  • 怎么做自动跳转网站wordpress主题显示不了
  • 赤峰住房城乡建设部网站软件程序开发公司
  • 学做美食视频网站网站建设后怎样发信息
  • 康复网站模板怎么做wordpress+网速
  • 推广网站怎么做模板厦门 网站建设 公司哪家好
  • 如何分析对手网站关键词小企业网站建设
  • 衡水微网站制作怎么做做网站放广告
  • 苏宁电器网站建设特点分析做电子商务网站注册哪一类商标
  • 南宁做网站优化的公司网站建设代码结构
  • 网站建设做网站好做吗网站上的动态背景怎么做的
  • 青岛市住房城乡建设厅网站网站首页怎么做ps