Android单例模式的四种实现⽅式⽬录
⼀.饿汉式
⼆.懒汉式
三.双重检查加锁⽅式
四.静态内部类⽅式
总结
⼀.饿汉式
public class SingletionStarving {
private static final SingletionStarving mInstance = new SingletionStarving();
private SingletionStarving() {
}
public static SingletionStarving getInstance() {
return mInstance;
}
}
构造函数⽤private修饰,外部⽆法访问
声明静态对象时就初始化
static关键字修饰,静态变量,存储在内存中,只有⼀份数据。
final关键字,只初始化⼀次,所以mInstance实例只有⼀个。
⼆.懒汉式
public class SingletionSlacker {
private static SingletionSlacker mInstance;
private SingletionSlacker() {}
public static synchronized SingletionSlacker getInstance() {
if (mInstance == null) {
mInstance = new SingletionSlacker();
}
return mInstance;
}
}
构造函数⽤private修饰,外部⽆法访问
使⽤的时候即调⽤getInstance的时候才初始化
static关键字修饰,静态变量,存储在内存中,只有⼀份数据。
synchronized线程安全,多线程情况下单例的唯⼀性
缺点:没次调⽤getInstance都会同步⼀次,浪费资源
三.双重检查加锁⽅式
⽹上建议和使⽤最多的⽅法
public class Singletion {
private static Singletion mInstance;
private Singletion() {}
public static Singletion getmInstance() {
if (mInstance == null) {
synchronized (Singletion.class) { if (mInstance == null) {
mInstance = new Singletion (); }
}
}
return mInstance;
}
}
构造函数⽤private修饰,外部⽆法访问
使⽤的时候即调⽤getInstance的时候才初始化
static关键字修饰,静态变量,存储在内存中,只有⼀份数据
synchronized线程安全,多线程情况下单例的唯⼀性
两次判断空,避免多次同步(synchronized)
单例模式的几种实现方式缺点
private static Singletion mInstance;
private Singletion() {}
public static Singletion getmInstance() {}
由于jvm特性,允许乱序执⾏,上⾯三句代码顺序不定,那么就可能出现失效的问题。
步骤⼀、倘若A线程执⾏getmInstance(),还没执⾏构造⽅法Singletion()
步骤⼆、此时B线程调⽤getmInstance()。因为A已经执⾏getmInstance(),所以mInstance不为空就直接获取。
步骤三、由于B直接获取,⽽真实情况是A线程构造⽅法还未执⾏,所以mInstance就为空了。
虽然此情况发⽣概率较⼩,但也是⼀种情况。为了解决这种情况,java1.6开始加⼊volatile关键字
private volatile static Singletion mInstance;
这样就避免了⽅式失效的情况。虽然会volatile消耗⼀些性能,所以最佳写法
public class Singletion {
private volatile static Singletion mInstance;
private Singletion () {}
public static Singletion getmInstance() { if (mInstance == null) {
synchronized (Singletion.class) { if (mInstance == null) {
mInstance = new Singletion(); }
}
}
return mInstance;
}
}
虽然volatile让⽅式完美,但是没有volatile关键字的写法基本能满⾜绝⼤部分情况。除⾮你要运⾏在⾼并发,或者java1.6之前的代码中。
四.静态内部类⽅式
public class SingletionInternalClass {
private SingletionInternalClass() {}
public static SingletionInternalClass getInstance() {
return SingletionInternalClassHolder.instance;
}
private static class SingletionInternalClassHolder {
private static final SingletionInternalClass instance = new SingletionInternalClass();
}
}
构造函数⽤private修饰,外部⽆法访问
使⽤的时候即调⽤getInstance的时候才初始化
调⽤getInstance才回去加载SingletionInternalClassHolder类,确保了线程安全,保证了单例的唯⼀性
总结
单例模式不管⽤那种⽅式实现,核⼼思想都相同
1、构造函数私有化,通过⼀次静态⽅法获取⼀个唯⼀实例
2、线程安全
最后推荐使⽤⽂中**双重锁⽅式和静态内部类的⽅式**来创建单例模式。
以上就是Android 单例模式的四种实现⽅式的详细内容,更多关于Android 单例模式的实现的资料请关注其它相关⽂章!
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论