两种语言实现设计模式(C++和Java)(二:单例模式)
本篇介绍单例模式,可以说是使用场景最频繁的设计模式了。可以根据实例的生成时间,分为饿汉模式和懒汉模式
饿汉模式:饿了肯定要饥不择食。所以在单例类定义的时候就进行实例化。
懒汉模式:故名思义,不到万不得已就不会去实例化类,也就是说在第一次用到类实例的时候才会去实例化
一.饿汉模式
1.c++
线程安全,不会内存泄漏的写法:
1 class Singleton 2 { 3 protected: 4 Singleton(){} 5 ~Singleton(){ 6 if (p == NULL) return; 7 delete p; 8 p = NULL; 9 } 10 private: 11 static Singleton* p; 12 public: 13 static Singleton* getInstance(){ 14 return p; 15 } 16 }; 17 Singleton* Singleton::p = new Singleton;
2.Java
1 public class Singleton { 2 private static Singleton singleton = new Singleton(); 3 private Singleton(){} 4 public static Singleton getInstance(){ 5 return singleton; 6 } 7 }
优点:饿汉模式天生是线程安全的,使用时没有延迟。
缺点:启动时即创建实例,启动慢,有可能造成资源浪费。
二.懒汉模式
1.c++
加锁的线程安全经典懒汉模式
1 class singleton{ 2 protected: 3 singleton(){ 4 pthread_mutex_init(&mutex, 0); 5 } 6 private: 7 static singleton* p; 8 public: 9 static pthread_mutex_t mutex; 10 static singleton* initance(){ 11 if (p == NULL) 12 { 13 pthread_mutex_lock(&mutex); 14 if (p == NULL) 15 p = new singleton(); 16 pthread_mutex_unlock(&mutex); 17 } 18 return p; 19 } 20 };
2.Java
加了synchronized达到线程安全
1 public class SingletonLazier { 2 3 private static SingletonLazier uniqueInstance = null; 4 5 private SingletonLazier(){ } 6 7 public static synchronized SingletonLazier getInstance(){ 8 if(uniqueInstance == null){ 9 uniqueInstance = new SingletonLazier(); 10 } 11 return uniqueInstance; 12 } 13 }
三.Holder模式
java的实现方式,由JVM实现线程安全性
1 public class Singleton { 2 3 private static class SingletonHolder{ 4 private static Singleton instance = new Singleton(); 5 } 6 7 private Singleton(){} 8 9 public static Singleton getInstance(){ 10 return SingletonHolder.instance; 11 } 12 }