首页 > 其他 > 详细

单例模式

时间:2019-08-02 01:44:11      阅读:90      评论:0      收藏:0      [点我收藏+]

1、恶汉模式:直接创建对象,不存在线程安全问题

  • 直接实例化恶汉模式(简洁直观)
  • /**
     * 恶汉模式:在类初始化时直接创建实例对象,不管你是否需要,都会创建这个对象
     *
     * (1)构造器私有化
     * (2)自行创建,并且用静态变量保存
     * (3)向外提供这个实例
     * (4)强调这是一个单利,所以我们用final修饰
     */
    public class SingleTon {
    
        public final static SingleTon INSTANCE = new SingleTon();
    
        private SingleTon(){
    
        }
    }
  • 枚举式(最简洁)
  • /**
     * 枚举类型:表示该类型的对象是有限的几个
     * 我们可以限定为一个,就成了单利
     */
    public enum SingleTon2 {
        INSTENCE
    }

     

  • 静态代码块恶汉模式(适合复杂实例化)

  应用实例:有可能需要加载某个文件中的信息

public class SingleTon3 {

    public final static SingleTon3 INSTANCE;

    private String info;

    static {
        try {
            Properties properties = new Properties();
            properties.load(SingleTon3.class.getClassLoader().getResourceAsStream("singel.properties"));
            INSTANCE = new SingleTon3(properties.getProperty("info"));
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    public String getInfo() {
        return info;
    }

    public void setInfo(String info) {
        this.info = info;
    }

    private SingleTon3(String info) {
        this.info = info;
    }


    @Override
    public String toString() {
        return "SingleTon3{" +
                "info=‘" + info + ‘\‘‘ +
                ‘}‘;
    }
}

2、懒汉模式:延迟创建对象

  1、存在线程安全问题

**
 * 懒汉模式:延迟创建实例对象
 *
 * (1)构造器私有化
 * (2)用一个静态变量保存这个唯一实例
 * (3)提供一个静态方法,获取这个实例对象
 *
 */
public class SingleTon4 {

    private static  SingleTon4 instance;
    private SingleTon4(){

    }

    public static SingleTon4 getInstance(){
        if (instance == null){
            try {
                Thread.sleep(100);
            }catch (InterruptedException e){
                e.printStackTrace();
            }

            instance = new SingleTon4();
        }
        return instance;
    }
}
public class TestSingleTon4 {
    public static void main(String[] args) throws Exception{
        /*SingleTon4 s4 = SingleTon4.getInstance();
        SingleTon4 s44 = SingleTon4.getInstance();
        System.out.println(s4 == s44);*/
        //存在线程安全问题
        Callable<SingleTon4> c = new Callable<SingleTon4>() {
            @Override
            public SingleTon4 call() throws Exception {
                return SingleTon4.getInstance();
            }
        };

        ExecutorService es =  Executors.newFixedThreadPool(2);

        Future<SingleTon4> f1 = es.submit(c);
        Future<SingleTon4> f2 = es.submit(c);

        SingleTon4 s1 = f1.get();
        SingleTon4 s2 = f2.get();


        System.out.println(s1 == s2);
        System.out.println(s1);
        System.out.println(s2);;
    }
}

结果

false
com.lk.SingleTon4@6d6f6e28
com.lk.SingleTon4@135fbaa4

解决线程不安全

public class SingleTon5 {

    private static SingleTon5 instance;

    private SingleTon5() {

    }

    public static SingleTon5 getInstance() {
        if (instance == null) {
            synchronized (SingleTon5.class) {
                if (instance == null) {
                    try {
                        Thread.sleep(100);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                    instance = new SingleTon5();
                }
            }
        }

        return instance;
    }
}

2、静态内部类实现(线程安全)

**
 * 在内部类加载和初始化时,才创建INSTANCE实例对象
 * 静态内部类不会自动随着外部的加载和初始化而初始化,他要单独加载和初始化
 * 因为是在内部类加载和初始化,创建的,是线程安全的
 */
public class SingleTon6 {
    private SingleTon6(){

    }
    private static class inner{
        private static final SingleTon6  INSTANCE = new SingleTon6();
    }

    public static SingleTon6 getInstance(){
        return  inner.INSTANCE;
    }
}

 

单例模式

原文:https://www.cnblogs.com/karrya/p/11286046.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!