什么是单例模式?
Java中单例模式定义;“一个类有且仅有一个实例,并且自行实例化向整个系统提供该实例。”
简单的说,这个类在系统中只存在唯一的一个对象,不像我们平时所创建的类,只要你new多少次,就有多少个不同的对象。
单例模式的应用
单例模式用在需要保持对象的唯一性的情况下,比如你的app保存设置信息,主题的数据类只能存在一个对象。比如说的你的加载进度条如果使用单例模式创建就会防止多余对象的创建导致不必要的内存占用。
如何实现单例模式?
单例模式存在多种实现方法,但核心步骤离不开这三步:
1.构造函数私有化
2.在类中创建一个本类对象
3.提供一个方法可以获取到该对象
具体实现:
饿汉式:
class Student{
private int age;
//该类中提供的本类对象
private static Student stu=new Student();
//构造函数私有化
private Student(){}
//获取对象方法
public static Student getInstance(){
return stu;
}
public void setAge(int age){
this.age=age;
}
public int getAge(){
return age;
}
}
饿汉式的特点是在该类初始化时,自动会实例化一个对象,这种方法是用的比较多的
懒汉式:
class Student{
<span style="white-space:pre"> </span>
<span style="white-space:pre"> </span>
<span style="white-space:pre"> </span>
<span style="white-space:pre"> </span> private int age;
<span style="white-space:pre"> </span> //该类中提供的本类对象
<span style="white-space:pre"> </span> private static Student stu;
<span style="white-space:pre"> </span> //构造函数私有化
<span style="white-space:pre"> </span> private Student(){}
<span style="white-space:pre"> </span> //获取对象方法,先判断是否实例化,如果没有再实例化对象
<span style="white-space:pre"> </span> public static Student getInstance(){
<span style="white-space:pre"> </span>
<span style="white-space:pre"> </span>if(stu==null){
<span style="white-space:pre"> </span>synchronized (Student.class) {
<span style="white-space:pre"> </span>stu=new Student();
<span style="white-space:pre"> </span>}
<span style="white-space:pre"> </span>
<span style="white-space:pre"> </span>}
<span style="white-space:pre"> </span>return stu;
<span style="white-space:pre"> </span> }
<span style="white-space:pre"> </span>
<span style="white-space:pre"> </span> public void setAge(int age){
<span style="white-space:pre"> </span> this.age=age;
<span style="white-space:pre"> </span> }
<span style="white-space:pre"> </span> public int getAge(){
<span style="white-space:pre"> </span> return age;
<span style="white-space:pre"> </span> }
<span style="white-space:pre"> </span>
<span style="white-space:pre"> </span>
}
懒汉式的特点就是在你需要这个对象时再去判断是否实例化了该对象,如果没有再去创建,这样就比较节省内存空间。但是这样做每次判断时会浪费许多资源,这并不算是一个很好的优化。
有没有更好的解决办法呢?
当然有:
class Student{
private int age;
//该类中提供的本类对象
private static class StudentHolder{
private static Student stu=new Student();
}
//构造函数私有化
private Student(){}
//获取对象方法,先判断是否实例化,如果没有再实例化对象
public static Student getInstance(){
return StudentHolder.stu;
}
public void setAge(int age){
this.age=age;
}
public int getAge(){
return age;
}
}
在第一次调用getInstance()时,它会读取StudentHolder.stu,这时会导致StudentHolder初始化,它初始化时会实例化一个Student对象,由于它是静态类,所以只会初始化一次,这就完美解决了如何延迟实例化静态类对象的问题。
感谢一下两位博主的讲解:
http://blog.csdn.net/woshizisezise/article/details/50358924
http://blog.csdn.net/hong15007046964/article/details/51907891