zoukankan      html  css  js  c++  java
  • C++11并发编程:多线程std::thread

    作者:蜗牛201
    出处:https://www.cnblogs.com/woniu201/
    本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接。
    如果文中有什么错误,欢迎指出。以免更多的人被误导。

    一:概述

    C++11引入了thread类,大大降低了多线程使用的复杂度,原先使用多线程只能用系统的API,无法解决跨平台问题,一套代码平台移植,对应多线程代码也必须要修改。现在在C++11中只需使用语言层面的thread可以解决这个问题。

    所需头文件<thread>

    二:构造函数

    1.默认构造函数

    thread() noexcept
    一个空的std::thread执行对象

    2.初始化构造函数

    template<class Fn, class... Args>
    explicit thread(Fn&& fn, Args&&... args);
    创建std::thread执行对象,线程调用threadFun函数,函数参数为args。

    复制代码
    1 void threadFun(int a)
    2 {
    3     cout << "this is thread fun !" << endl;
    4 }
    5 
    6 thread t1(threadFun, 2);
    复制代码

    3.拷贝构造函数

    thread(const thread&) = delete;
    拷贝构造函数被禁用,std::thread对象不可拷贝构造

    复制代码
    1 void threadFun(int& a)
    2 {
    3     cout << "this is thread fun !" << endl;
    4 }
    5     
    6 int value = 2;
    7 thread t1(threadFun, std::ref(value));
    复制代码

    4.Move构造函数

    thread(thread&& x)noexcept
    调用成功原来x不再是std::thread对象

    复制代码
    1 void threadFun(int& a)
    2 {
    3     cout << "this is thread fun !" << endl;
    4 }
    5 
    6 int value = 2;
    7 thread t1(threadFun, std::ref(value));
    8 thread t2(std::move(t1));
    9 t2.join();
    复制代码

    三:成员函数

    1.get_id()

    获取线程ID,返回类型std::thread::id对象。

    复制代码
     1 thread t1(threadFun);
     2 thread::id threadId = t1.get_id();
     3 cout << "线程ID:" << threadId << endl;
     4 
     5 //threadId转换成整形值,所需头文件<sstream>
     6 ostringstream   oss;
     7 oss << t1.get_id();
     8 string strId = oss.str();
     9 unsigned long long tid = stoull(strId);
    10 cout << "线程ID:" << tid << endl;
    复制代码

    2.join()

    创建线程执行线程函数,调用该函数会阻塞当前线程,直到线程执行完join才返回。

    thread t1(threadFun);
    t1.join()  //阻塞等待

    3.detach()

    detach调用之后,目标线程就成为了守护线程,驻留后台运行,与之关联的std::thread对象失去对目标线程的关联,无法再通过std::thread对象取得该线程的控制权。

    4.swap()

    交换两个线程对象

    复制代码
    1 thread t1(threadFun1);
    2 thread t2(threadFun2);
    3 cout << "线程1的ID:" << t1.get_id() << endl;
    4 cout << "线程2的ID:" << t2.get_id() << endl;
    5 
    6 t1.swap(t2);
    7 
    8 cout << "线程1的ID:" << t1.get_id() << endl;
    9 cout << "线程2的ID:" << t2.get_id() << endl;
    复制代码

    5.hardware_concurrency()

    获得逻辑处理器储量,返回值为int型

     1 int coreNum = thread::hardware_concurrency(); 

    四:使用

     1.创建线程

    复制代码
     1 void threadFun1()
     2 {
     3     cout << "this is thread fun1 !" << endl;
     4 }
     5 
     6 int main()
     7 {
     8     thread t1(threadFun1);
     9     t1.join();
    10 
    11     getchar();
    12     return 1;
    13 }
    复制代码

    2.创建线程,传参

    复制代码
     1 void threadFun1(int v)
     2 {
     3     cout << "this is thread fun1 !" << endl;
     4     cout << v << endl;
     5 }
     6 
     7 int main()
     8 {
     9     int value = 6;
    10     thread t1(threadFun1, value);
    11     t1.join();
    12 
    13     getchar();
    14     return 1;
    15 }
    复制代码

    需要注意,变量int value 和int v 做变量传递时并不是引用,而是对变量做了拷贝,所以在传递给int v前,int value不能出作用域(释放了内存),join(),可以保证int value变量释放内存,如果使用detach(),可能存在这种情况。

    3.创建线程,引用传参

    复制代码
     1 void threadFun1(int& v)
     2 {
     3     cout << "this is thread fun1 !" << endl;
     4     cout << v << endl;
     5 }
     6 
     7 int main()
     8 {
     9     int value = 6;
    10     thread t1(threadFun1, std::ref(value));
    11     t1.join();
    12 
    13     getchar();
    14     return 1;
    15 }
    复制代码

    4.创建建线程,线程函数为类成员函数

    复制代码
     1 class Object
     2 {
     3 public:
     4     Object()
     5     {
     6         cout << "构造函数" << endl;
     7     }
     8 
     9     ~Object()
    10     {
    11         cout << "析构函数" << endl;
    12     }
    13 
    14     void fun(string info)
    15     {
    16         cout << info << endl;
    17     }
    18 
    19 };
    20 
    21 int main()
    22 {
    23 
    24     Object obj;
    25     string str = "我是一个类的成员函数!";
    26     thread t1(&Object::fun, &obj, str);
    27     t1.join();
    28 
    29     getchar();
    30     return 1;
    31 }
    复制代码

  • 相关阅读:
    和我一起看API(一)你所不知道的LinearLayout补充
    SQLSERVER常见系统函数之字符串函数(一)
    C#使用ADO.NET访问数据库(一)
    SQLSERVER基础语句(一)
    Vue 项目部署之iis
    XiaoQi.Study 之 .net core webapi (三)
    XiaoQi.Study 之 .net core webapi (二)
    XiaoQi.Study 之.net core webapi(一)
    Vue 学习笔记(四)
    Vue 学习笔记(二)
  • 原文地址:https://www.cnblogs.com/buzhidao1/p/13409919.html
Copyright © 2011-2022 走看看