最近在学习单例模式,在了解频繁加锁会造成资源的浪费的前提下,通常做法时使用
双重检查的机制来解决资源浪费。于是我做了以下测试:
#include <unistd.h>
#include <pthread.h>
#include <iostream>
#include <vector>
#include <sys/time.h>
using namespace std;
pthread_mutex_t lo;
class Singleton
{
public:
static Singleton * p_instance;
static Singleton * GetInstance();
private:
Singleton(){cout<<"Contructor running"<<endl;}
};
Singleton * Singleton::p_instance=NULL;
Singleton * Singleton::GetInstance()
{
if(p_instance==NULL)
{
pthread_mutex_lock(&lo);
if(p_instance==NULL)
p_instance=new Singleton();
pthread_mutex_unlock(&lo);
}
pthread_mutex_unlock(&lo);
return p_instance;
}
void * fun(void *)
{
Singleton::GetInstance();
}
int main()
{
//cout<<&lo<<endl;
pthread_mutex_init(&lo,NULL);
vector<pthread_t *> thread_pool;
for(int i=0;i<10000000;i++)
{
pthread_t * pth = new pthread_t;
thread_pool.push_back(pth);
}
//calculate time duration
struct timeval t1,t2;
double duration=0;
gettimeofday(&t1,NULL);
for(int i=0;i<thread_pool.size();i++)
{
pthread_create(thread_pool[i],NULL,fun,NULL);
}
for(int i=0;i<thread_pool.size();i++)
pthread_join(*thread_pool[i],NULL);
gettimeofday(&t2,NULL);
duration = t2.tv_sec - t1.tv_sec + (t2.tv_usec - t1.tv_usec)/1000000.0;
cout<<duration<<endl;
return 0;
}
结果在ubuntu18.04中测试耗时:14.907s
然后我将程序中的,第一个判空去掉,就像这样:
Singleton * Singleton::GetInstance()
{
//if(p_instance==NULL)
//{
pthread_mutex_lock(&lo);
if(p_instance==NULL)
p_instance=new Singleton();
// pthread_mutex_unlock(&lo);
//}
pthread_mutex_unlock(&lo);
return p_instance;
}
同样地,进行了多次返回的结果是:
Contructor running
18.1153
me@ubuntu:~/Desktop/pocesstet$ ./app
Contructor running
14.9578
me@ubuntu:~/Desktop/pocesstet$ ./app
Contructor running
14.8444
me@ubuntu:~/Desktop/pocesstet$ ./app
Contructor running
14.3856
时间时间甚至比使用双重检查(double check)的效果要好?这是为什么?
是我哪里理解错了吗?先谢谢各位了!