一、创建多个线程
1.多个线程执行顺序是乱的,跟操作系统对线程的运行调度机制有关(运行调度机制很复杂)。
2.主线程等待所有子线程运行结束,推荐join()写法,更容易写出稳定的程序。
3.把 thread对象放在容器里管理,看起来像个对象数组,这对我们一次创建大量的线程并对大量的线程进行管理。
#include <iostream>
#include <thread>
#include <vector>
using namespace std;
void myprint(int inum)
{
cout<<"myprint thread begin,inum="<<inum<<endl;
cout<<"myprint thread end,inum="<<inum<<endl;
return ;
}
int main(){
vector<thread> mythreads;
for(int i=0;i<10;i++){
mythreads.push_back(thread(myprint,i));
}
for(auto iter=mythreads.begin();iter!=mythreads.end();iter++){
iter->join();
}
cout<<"I Love China!"<<endl;
return 0;
}
myprint thread begin,inum=myprint thread begin,inum=01
myprint thread end,inum=
myprint thread end,inum=1
myprint thread begin,inum=3
myprint thread end,inum=3
myprint thread begin,inum=5
myprint thread end,inum=5
myprint thread begin,inum=06
myprint thread end,inum=6
myprint thread begin,inum=7
myprint thread end,inum=7
myprint thread begin,inum=4myprint thread begin,inum=
myprint thread end,inum=4
myprint thread begin,inum=9
myprint thread end,inum=9
myprint thread begin,inum=2
myprint thread end,inum=2
8
myprint thread end,inum=8
I Love China!
二、数据共享问题分析
2.1 只读的数据
只读数据,是安全稳定的,不需要特别的处理手段,直接读就可以。
2.2 有读有写的数据
2个线程写,8个线程读,如果代码写的不好,那么程序肯定崩溃;最简单的不崩溃的,读的时候不能写,写的时候不能读。由于任务切换导致诡异事情发生,最可能发生的诡异事情还是崩溃。
2.3其他案例
过马路的十字路口,买火车票定同一个座位等等。
三:共享数据的保护案例代码
#include <iostream>
#include <thread>
#include <vector>
#include <list>
#include <mutex>
using namespace std;
class A
{
public:
void inMsgRecvQueue()
{
for(int i=0;i<100000;i++){
cout<<"inMsgRecvQueue() begin,insert a element:"<< i<<endl;
msgRecvQueue.push_back(i);
}
}
void outMsgRecvQueue()
{
for(int i=0;i<10000;i++)
{
if(!msgRecvQueue.empty())
{
int command = msgRecvQueue.front();
msgRecvQueue.pop_front();
}
else
{
cout<<"outMsgRecvQueue() is empty:"<<i<<endl;
}
}
}
private:
list<int> msgRecvQueue;
};
int main(){
A myobja;
thread myOutMsgObj(&A::outMsgRecvQueue,&myobja);
thread myInMsgObj(&A::inMsgRecvQueue,&myobja);
myOutMsgObj.join();
myInMsgObj.join();
return 0;
}