简介
C++ 标准库集成了多线程并行处理的功能,可以非常简单实现多线程并行处理。 C++ 11 没有提供线程池,想用的话需要自己手动实现。但是一般用C++完成多线程处理时,并发量往往不是很大,所以不用线程池,效率也不会受到很大影响,如果并发量很大,直接用java更合适。
每个应用程序至少有一个进程,而每个进程至少有一个主线程,除了主线程外,在一个进程中还可以创建多个线程。每个线程都需要一个入口函数,入口函数返回退出,该线程也会退出,主线程就是以main函数作为入口函数的线程。在C++ 11的线程库中,将线程的管理在了类std::thread中,使用std::thread可以创建、启动一个线程,并可以将线程挂起、结束等操作。
C++ 11的线程库启动一个线程是非常简单的,只需要创建一个std::thread对象,就会启动一个线程,并使用该std::thread对象来管理该线程。
比如:
void do_task()
{
std::cout<<"0,1,2,3"<<std::endl;
}
std::thread a(do_task); //立即启动一个线程。
a.detach();
这里创建std::thread传入的函数,实际上其构造函数需要的是可调用(callable)类型,只要是有函数调用类型的实例都是可以的,包括void函数,带形参的void函数,带返回值的函数,带返回值和形参的函数,还可以使用lamba 函数,或是重载了运算符“()”的类。
当线程启动后,一定要在和线程相关联的thread销毁前,确定以何种方式等待线程执行结束。C++11有两种方式来等待线程结束
(1)detach方式,启动的线程自主在后台运行,当前的代码继续往下执行,不等待新线程结束。前面代码所使用的就是这种方式。
(2)join方式,等待启动的线程完成,才会继续往下执行。假如前面的代码使用这种方式,其输出就会0,1,2,3,因为每次都是前一个线程输出完成了才会进行下一个循环,启动下一个新线程。
实现
方式一 :定义一个多线程处理的函数
#include<thread>
#include<mutex>
void Thread_Work1( )
{
定义你想要在子线程执行的函数。函数可以引用全局变量。
}
void Thread_Work2(int i, int j, int k,std::map<int,int> &Map1, std::map<int, int> Map2)
{
std::cout << "Thread Id : " << std::this_thread::get_id() << "; " << i + j + k << endl;
for (std::map<int, int>::iterator iter = Map1.begin(); iter != Map1.end(); iter++)
{
std::cout << iter->second << endl;
iter->second++;
}
for (std::map<int, int>::iterator iter = Map2.begin(); iter != Map2.end(); iter++)
{
std::cout << iter->second << endl;
iter->second++;
}
}
double Thread_Work3( 形参列表 )
{
auto id =std::this_thread::get_id(); 获取执行此函数的当前线程的线程号。
定义你想要在子线程执行的函数。函数可以引用全局变量。
}
void main()
{
std::thread s1( Thread_Work1 ); //只需要创建一个std::thread对象,就会立即启动一个线程,并使用 s1 这个实例管理该线程。
s1.get_id(); //获取线程id
s1.join(); //等待线程运行结束。
std::map<int, int> My_Map1;
My_Map1