有两个类
class TestClass
{
public: TestClass(); map<int,int> int_map;
};
class TestClass2
{
public: TestClass2(TestClass* tc); void Run(); TestClass* tc1;
};
TestClass::TestClass()
{
printf("TestClass1 addr :%p \n",this);
}
TestClass2::TestClass2(TestClass* tc){
tc1 = tc;printf("TestClass2 get TestClass1 ,addr :%p !\n",tc1);
}
void TestClass2::Run(){
int i = 0; while(true){ tc1->int_map.insert(make_pair(i,1)); printf("TestClass2:size of TestClass1 %p 's int_map is %d!\n",tc1,tc1->int_map.size()); sleep(2); i++;}
}
int main()
{
TestClass* tc1 = new TestClass();printf("tc1 addr is %p!\n",tc1);TestClass2* tc2 = new TestClass2(tc1);pid_t pid = fork();if(pid == 0){ while(1){ sleep(1); printf("TestClass1 :%p int_map size %d!\n",tc1,tc1->int_map.size()); }}else{ tc2->Run();}
}
TestClass2 初始化后获得TestClass对象的指针,
通过这个指针来访问TestClass中的map,
每次访问后打印size
两个类在不同的线程打印,按理说size应该一样,
结果TestClass2可以输出数量,而TestClass自己本身却输出0
解决方案
- 如果你的本意是验证多线程情况下对共享资源的访问,那你代码实现有误,
fork()
是派生一个子进程和线程没啥关系,而子进程拷贝了一份父进程环境变量和对象信息,已经和父进程的没啥关系了;u3000c++11提供了线程库,直接取用 - 修改了一下你的代码(完整见这里),实际上是可以观测到共享数据的修改的.
TestClass* tc1 = new TestClass(); printf("tc1 addr is %p!\n",tc1); TestClass2* tc2 = new TestClass2(tc1); std::thread t([&](){tc2->Run();}); t.detach(); do { std::this_thread::sleep_for(1s); cout<<"TestClass1:size of TestClass1 tc1->int_map size:"<<tc1->int_map.size()<<std::endl; } while(true);
结果如下:
tc1 addr is 0x1ee1c20!
TestClass2 get TestClass1, addr0x1ee1c20
TestClass2:size of TestClass1 tc1->int_map size:1
TestClass1:size of TestClass1 tc1->int_map size:1
TestClass2:size of TestClass1 tc1->int_map size:2
TestClass1:size of TestClass1 tc1->int_map size:2
TestClass1:size of TestClass1 tc1->int_map size:2
TestClass2:size of TestClass1 tc1->int_map size:3
TestClass1:size of TestClass1 tc1->int_map size:3
TestClass1:size of TestClass1 tc1->int_map size:3