设计模式之单例模式

说起设计模式,java中总共有23中设计模式,我们最常见的也就属于单例设计模式了,它也是最简单的设计模式。

首先,什么是单例设计模式?    单例设计模式是在程序运行过程中,该程序中只能存在该类的一个对象。

单例设计模式书写方法:1. 构造方法私有化    2. 提供静态的方法供外部调用

单例设计模式的书写方式有很多中,比较常见的就是饿汉式和懒汉式。

饿汉式:

public class Singleton {

    private static Singleton mInstance = new Singleton();

    private Singleton() {

    }

    public static Singleton getInstance() {

        return mInstance;

    }

}

这种方式在类加载的时候就会创建对象,容易造成内存浪费。执行效率高,线程安全。


懒汉式:

public class Singleton {

private static SingletonmInstance =null;

    private Singleton() {

}

public static SingletongetInstance() {

if (mInstance ==null) {

mInstance =new Singleton();

        }

return mInstance;

    }

}

在调用的时候才会创建对象,但是线程不安全。多线程调用时会出现问题。

public class Singleton {

private static SingletonmInstance =null;

    private Singleton() {

}

public static SingletongetInstance() {

if (mInstance ==null) {

synchronized (Singleton.class) {

if (mInstance ==null) {

mInstance =new Singleton();

                }

}

}

return mInstance;

    }

}

在获取对象时加上synchronized关键字,能够保证在多线程调用时不会出现线程安全问题,但是相对来说效率较低。但这种方式并不完善,还是会极小概率出现问题。

由于java在创建对象时有以下三个步骤:

    1. 开辟一块内存空间

    2. 初始化对象

    3. 将初始化好的对象指向内存空间

然而这个执行顺序并非固定,有可能会按照1->2->3的顺序执行,也有可能会执行1->3->2的顺序。当按照132顺序执行时,会导致对象未被初始化就指向了内存空间,从而出现问题。此使使用volatile关键字,可以有效避免这个问题。

volatile关键字的作用主要有以下两点:

    1. 防止指令重排序

    2. 保持内存可见性

因此修改后的代码如下:

public class Singleton {

private volatile static SingletonmInstance =null;

    private Singleton() {

}

public static SingletongetInstance() {

if (mInstance ==null) {

synchronized (Singleton.class) {

if (mInstance ==null) {

mInstance =new Singleton();

                }

}

}

return mInstance;

    }

}

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容