黑马程序员_Singleton模式(单例模式)饿汉式和懒汉式
2015-06-06 23:11
381 查看
------- android培训、java培训、期待与您交流! ----------
单例设计模式
2.2、让复杂的问题简单化;
5.2、禁止其他的程序建立对象,由自己来建立对象;
5.3、为了让其他程序可以访问到该类对象,只好在本类中,自定义一个对象;
5.4、为了方便其他程序对自定义对象的访问,可以对外提供一些访问方式;
6.2、在类中创建一个本类对象;
6.3、提供一个方法可以获取到该对象;
设置的是s1的值是30,而打印的是s2的值也是30,由此可以s1和s2所指向的是同一个对象;
举例:
运行后的结果:
2.1、安全,简单;
6、懒汉式的特点
刚开始不建立对象,如果什么时候需要,那么就什么时候建立对象;
如果遇到多线程时,当A程序读到getInstance的方法的时候,当cpu执行到s==null时,但是这时cpu切换到去处理B程序了,但是这时A程序就处于休息状态,没有执行程序,但是这时B程序同样也进来了,判断了s==null也是满足条件的,现在A程序醒了,然后执行了s
= new Single();创建了一个对象,这是B程序也醒了,又创建了一个对象;换句话说就是现在内存中的对象已经不唯一了,懒汉式在多线程访问时会出现安全隐患;
8.2、措施:
在函数上加上一个锁就是Synchronized,这时如果A程序进来之后,但是B程序就不可以进入程序了,A程序创建了对象之后,然后返回了,这时B程序判断s已经不等于null,那么就不再执行程序了。但是在这个锁加载函数上面,每一个线程都要先进行判断一下,效率比较低效;这时如何能够既能可以保证对象的唯一性又能解决低效的问题?用双重判断来解决:判断锁的次数减少了;
答:懒汉式的特点在于实例的延时加载。
9.2、问:懒汉式的延迟加载有没有问题?
答:有,如果多线程访问时,会出现安全问题。
9.3、问:出现了安全问题怎么解决?
答:可以加同步来解决,而加同步的方式有两种,同步代码快和同步函数都行,但是稍微有些低效,用双重判断的形式可以解决效率的问题。
9.4、问:加同步的时候使用的锁是哪一个?
答:该类所属的字节码文件对象。
2、使用单例延时加载的时候,保证对象的唯一性,以及用双重判断来提高效率;
3、饿汉式的特点:对象先进行初始化;懒汉式的特点:对象后进行初始化;
4、懒汉式如何在多线程访问时解决安全隐患。
5、懒汉式的面试题;
单例设计模式
第一部分:
1、设计模式的概念:
每一个模式描述了一个在我们周围不断重复发生的问题,以及该问题的解决方案的核心。这样,你就能一次有一次地使用该方案而不必做重复劳动;而模式就是解决某一类问题最行之有效的方案;这是一个纯粹偏思想的,在不断的劳动的过程中总结出来的。2、设计模式的特点:
2.1、将某一类问题解决起来会变的更简单;2.2、让复杂的问题简单化;
3、单例设计模式:
解决一个类在内存中存在一个对象;换句话说就是在一个类中只能有一个对象,不可能会出现第二个对象;4、单例设计模式的由来:
现在有两个程序,分别是A程序和B程序,当A程序要操作一个文件的时候,这是就要new一个对象,当B文件也要操作一个文件的时候,同样也要new一个新的对象,但是A和B操作的不是同一个对象,因此这时要保证对象的唯一性;5、单例设计模式的思想:
5.1、为了避免其他程序过多建立该类对象,先禁止其他程序建立该类对象;5.2、禁止其他的程序建立对象,由自己来建立对象;
5.3、为了让其他程序可以访问到该类对象,只好在本类中,自定义一个对象;
5.4、为了方便其他程序对自定义对象的访问,可以对外提供一些访问方式;
6、单例设计模式的步骤:
6.1、将构造函数进行私有化;6.2、在类中创建一个本类对象;
6.3、提供一个方法可以获取到该对象;
7、代码表现:
<span style="font-size:18px;">class Single { private int num; public void setNum(int num) { this.num = num; } public int getNum() { return num; } // 将构造函数进行私有化; private Single(){} // 创建一个本类对象; private static Single s = new Single(); // 返回的是一个Single类型的对象; public static Single getInstance()//一个类类型的 { return s; } } class SingleDemo { public static void main(String[] args) { // 类名调用静态方法 Single s1 = Single.getInstance(); Single s2 = Single.getInstance(); // Single s1 = new Single(); // Single s2 = new Single(); s1.setNum(30); System.out.println(s2.getNum()); // Single ss =Single.getInstance(); } } /* 打印的是30,说明s1 和s2 指向的是同一个对象 */</span><span style="font-size:24px;font-weight: bold;"> </span>
8、运行的结果:
设置的是s1的值是30,而打印的是s2的值也是30,由此可以s1和s2所指向的是同一个对象;
9、图形展示:
10、单例设计模式应用:
对于事物该怎么描述,还是怎么描述,当需要将该事物的对象保证在内存中唯一性时,就加入单例设计模式思想即可;举例:
class Student { private int age;//要将属性进行私有化 public void setAge(int age) { this.age = age; } public int getAge() { return age; } // 要求保证在内存中的唯一性,那么就加上下面的三步 private Student(){} private static Student s = new Student(); public static Student getInstance() { return s; } } class SingleStudentDemo { public static void main(String[] args) { // 调用静态方法; Student s1 = Student.getInstance(); Student s2 = Student.getInstance(); s1.setAge(34); System.out.println(s2.getAge()); } }
运行后的结果:
第二部分:
1、饿汉式
先初始化对象,开发一般会用饿汉式2、饿汉式特点
2.1、Single类进内存,对象还没有存在,就已经创建好了对象;2.1、安全,简单;
3.饿汉式代码体现
<span style="font-size:14px;">//第一种,这个是先初始化对象 //称为:饿汉式 class Single { private Single(){} private static Single s = new Single(); public static Single getInstance() { return s; } }</span>
4、懒汉式
对象是方法被调用时,才初始化,也就做对象的延时加载;5、延时加载
特点:Single类进内存,对象还没有存在,只有调用了getInstance方法时,才建立对象;6、懒汉式的特点
刚开始不建立对象,如果什么时候需要,那么就什么时候建立对象;
7、懒汉式代码体现
//第二种,对象是方法调用时,才初始化,也叫做对象的延时加载,称为懒汉式 class Single { private Single(){} private static Single s =null; public static Single getInstance() { if(s==null) { synchronized(Single.class) { if(s==null) s = new Single(); } } return s; } } class SingleDemo { public static void main(String[] args) { Single ss = Single.getInstance(); } }
8、懒汉式的缺陷
8.1、缺陷:如果遇到多线程时,当A程序读到getInstance的方法的时候,当cpu执行到s==null时,但是这时cpu切换到去处理B程序了,但是这时A程序就处于休息状态,没有执行程序,但是这时B程序同样也进来了,判断了s==null也是满足条件的,现在A程序醒了,然后执行了s
= new Single();创建了一个对象,这是B程序也醒了,又创建了一个对象;换句话说就是现在内存中的对象已经不唯一了,懒汉式在多线程访问时会出现安全隐患;
8.2、措施:
在函数上加上一个锁就是Synchronized,这时如果A程序进来之后,但是B程序就不可以进入程序了,A程序创建了对象之后,然后返回了,这时B程序判断s已经不等于null,那么就不再执行程序了。但是在这个锁加载函数上面,每一个线程都要先进行判断一下,效率比较低效;这时如何能够既能可以保证对象的唯一性又能解决低效的问题?用双重判断来解决:判断锁的次数减少了;
9、面试
9.1、问:懒汉式和饿汉式有什么不同?答:懒汉式的特点在于实例的延时加载。
9.2、问:懒汉式的延迟加载有没有问题?
答:有,如果多线程访问时,会出现安全问题。
9.3、问:出现了安全问题怎么解决?
答:可以加同步来解决,而加同步的方式有两种,同步代码快和同步函数都行,但是稍微有些低效,用双重判断的形式可以解决效率的问题。
9.4、问:加同步的时候使用的锁是哪一个?
答:该类所属的字节码文件对象。
第三部分
我的总结:
1、定义单例的时候建议使用饿汉式,因为饿汉式不会出问题,简单安全;2、使用单例延时加载的时候,保证对象的唯一性,以及用双重判断来提高效率;
3、饿汉式的特点:对象先进行初始化;懒汉式的特点:对象后进行初始化;
4、懒汉式如何在多线程访问时解决安全隐患。
5、懒汉式的面试题;
相关文章推荐
- 黑马程序员————List集合概述、Arrayist集合、Vector集合、LinkedList集合简述
- 黑马程序员——多线程
- 程序员角度--自上而下看外设
- 黑马程序员——Java基础---集合(泛型及增强for)
- 黑马程序员————Map集合类总结、HashMap类、linkedHashMap类、TreeMap类
- 黑马程序员——Java基础——面向对象(继承、接口、多态)
- 面试题:异常注意事项
- 菜鸟程序员对学习编程语言的小小看法
- "菜鸟"与大神程序员之间的差别(转载)
- 黑马程序员——Java基础---多线程<二>
- 黑马程序员—数组及内存结构使用
- 黑马程序员——Java基础---多线程<一>
- 黑马程序员java学习笔记——String字符串及StringBubuffer容器
- 黑马程序员_static关键字
- 面试题:交换2个数字,要求高效快速.(可用三种方式实现交换2个数字)
- 面试题:说说或运算、异或运算
- 黑马程序员-18-java基础-多线程(1)-线程与同步
- Java的五个基础面试题 容易搞倒老手的
- LeetCode中有技巧的题需要面试前记得的
- Mysql面试题及答案