一,设计模式的由来:
设计模式的概念首先来源于其它行业:建筑业,在早起建房子的时候,肯定是经验缺乏、显得杂乱无序的,这就会造成很多问题,在行业发展过程,通过不断的经验积累,前辈们针对这些问题提出了合理解决方案,这就是设计模式,参照设计模式往往可以解决很多问题,在计算机编程方面,也会出现类似问题,所以牛人们把这些解决问题的方案进行归类和总结,形成了面向对象编程的23种设计模式。
1.11,什么是单例设计模式:
保证类在内存中只有一个对象。
1.1.2,饿汉式 开发用这种方式:
1 //饿汉式 2 class Singleton { 3 //1,私有构造函数 4 private Singleton(){} 5 //2,创建本类对象 6 private static Singleton s = new Singleton(); 7 //3,对外提供公共的访问方法 8 public static Singleton getInstance() { 9 return s; 10 } 11 12 public static void print() { 13 System.out.println("11111111111"); 14 } 15 }
1.1.3,懒汉式 面试写这种方式。多线程的问题?
懒汉式,单例的延迟加载模式
1 class Singleton { 2 //1,私有构造函数 3 private Singleton(){} 4 //2,声明一个本类的引用 5 private static Singleton s; 6 //3,对外提供公共的访问方法 7 public static Singleton getInstance() { 8 if(s == null) 9 //线程a进入等待,线程b进入等待,线程ab假如苏醒就会创建俩对象这就不是单例设计模式了 10 s = new Singleton(); 11 return s; 12 }
1.1.4,利用final完成的单例设计模式:
1 class Singleton { 2 private Singleton() {} 3 4 public static final Singleton s = new Singleton();//final是最终的意思,被final修饰的变量不可以被更改 5 }
1.1.5,懒汉式同步锁(懒汉式线程不安全的解决方案):
1 public class Singleton { 2 private static Singleton instance = null; 3 private Singleton(){}; 4 public static synchronized Singleton getInstance(){ 5 if(instance == null){ 6 instance = new Singleton(); 7 } 8 return instance; 9 }
问题:每次调用getInstance时都会判断锁,这样会降低程序的效率。注:锁(Singleton.class)该类所属的字节码文件对象。
1.1.6,懒汉式双重校验锁:
1 private static Singleton instance = null; 2 private Singleton(){}; 3 public static Singleton getInstance(){ 4 if(instance == null){ 5 synchronized(Singleton.class){ 6 if(instance == null){ 7 instance = new Singleton(); 8 } 9 return instance; 10 } 11 } 12 } 13 }
假如单单去讲上面的例子可能会有很多同学不明白,下面写一个平时开发用的单例设计模式的例子:
1.2.2,使用前:
1 public class Demo2_Singleton { 2 public static void main(String[] args) { 3 Studen s = new Studen(); 4 s.setName("JAVA大法好"); 5 s.setAge(100); 6 System.out.println(s.getName()+"~~~~~~"+s.getAge()); 7 } 8 } 9 class Studen{ 10 private String name; 11 private int age; 12 public Studen() { 13 super(); 14 // TODO Auto-generated constructor stub 15 } 16 public Studen(String name, int age) { 17 super(); 18 this.name = name; 19 this.age = age; 20 } 21 public String getName() { 22 return name; 23 } 24 public void setName(String name) { 25 this.name = name; 26 } 27 public int getAge() { 28 return age; 29 } 30 public void setAge(int age) { 31 this.age = age; 32 } 33 }
//编译结果:JAVA大法好~~~~~~100
1.2.3使用后:
1 public class Demo2_Singleton { 2 public static void main(String[] args) { 3 // 这样就可以看的出单例设计模式的好处,本类只存在一个实例,获取对象的属性不用new了,大大节省了内存空间,保证了对象的唯一性 4 Studen s = Studen.getInstance(); 5 s.setName("JAVA大法好"); 6 s.setAge(100); 7 System.out.println(s.getName()+"~~~~~~"+s.getAge()); 8 } 9 } 10 class Studen{ 11 private String name; 12 private int age; 13 private Studen() {}//私有构造方法 14 private static Studen instance = new Studen();//2.本类中创建该类的对象 15 public static Studen getInstance(){//3.创建一个方法,向外部提供该类的对象 16 return instance; 17 } 18 19 public String getName() { 20 return name; 21 } 22 public void setName(String name) { 23 this.name = name; 24 } 25 public int getAge() { 26 return age; 27 } 28 public void setAge(int age) { 29 this.age = age; 30 } 31 }
//编译结果:JAVA大法好~~~~~~100
二,饿汉式与懒汉式的区别:
1.6.1:懒汉式是空间换时间,懒汉式是时间换空间
1.6.2:在多线程访问中,饿汉式不会创建多个对象,而懒汉式有可能会创建多个对象