zoukankan      html  css  js  c++  java
  • Java中的单例模式

     一、饿汉式

    public class HungerySingleton {
     
     
        //ClassLoader 类加载时立即实例化对象,仅实例化一次,线程安全的
        private static HungerySingleton hungerySingleton = new HungerySingleton();
     
     
        public static HungerySingleton getInstance(){
            return hungerySingleton;
        }
     
        //利用线程输出(后面就不写了哈)
        public static void main(String[]args){
            for(int i=0;i<20;i++){
                Thread thread =new Thread() {
                    @Override
                    public void run() {
                        HungerySingleton hungerySingleton = HungerySingleton.getInstance();
                        System.out.println(hungerySingleton);
                    }
                };
                thread.start();
            }
        }
    }

    优点:仅实例化一次,线程是安全的。获取实例的速度快

    缺点:类加载时立即实例化对象,可能实例化的对象不被使用,造成内存的浪费。
     
     

    二、懒汉式

    public class HoonSingleton {
        //不能保证实例对象的唯一性
        private static HoonSingleton hoonSingleton = null;
     
     
        public static HoonSingleton getInstance(){
            if(hoonSingleton==null){
                hoonSingleton = new HoonSingleton();
            }
            return hoonSingleton;
        }
    }

    优点:获取实例时才进行实例的初始化,节省系统资源

    缺点:1、如果获取实例时,初始化的工作量较多,加载速度会变慢,影响系统系能
              2、每次获取实例都要进行非空检查,系统开销大
              3、非线程安全。注意红色代码标记,当多个线程同时getInstance()时,可能hoonSingleton实例化未完成,hoonSingleton==null判断均为true,造成对象重复实例化。
     
     

    三、双重检查锁 DCL(double-checked locking)+ volatile

    public class HoonSingleton {
     
        private static volatile HoonSingleton hoonSingleton = null;
     
        // 使用sync同步HoonSingleton.class 两次判断hoonSingleton是否为null 避免并发导致hoonSingleton被重新实例化
        // 并没有对整个方法使用sync,锁的粒度变小了,实现了实例对象的唯一性
        public static HoonSingleton getInstance(){
            if(hoonSingleton==null){
                synchronized (HoonSingleton.class) {
                    if(hoonSingleton==null) {
                        hoonSingleton = new DCL();
                    }
                }
            }
            return hoonSingleton;
        }

    优点:1、线程安全。注意加粗标记,进行双重检查,保证只在实例未初始化前进行同步,效率高。

              2、对hoonSingleton使用volatile修饰符,避免实例化过程中产生的重排序。避免NPE抛出。
    缺点:实例非空判断,耗费一定资源
     
     

    四、Holder方式 广泛使用的一种单例模式

    //声明类的时候、成员变量中不声明实例变量,而是放到内部静态类中
    public class HolderDemo {
     
        private static class Holder{
            private static HolderDemo instance = new HolderDemo();
        }
     
        public static HolderDemo getInstance(){
            return Holder.instance;
        }
    }

    优点:1、内部类只有在外部类被调用才加载,从而实现了延迟加载

              2、线程安全。且不用加锁。
     
     
     

    五、使用枚举的单例模式,本质上和饿汉模式没有任何区别,只是采用Enum实现的更巧妙了

    public enum EnumSingleton {
        //枚举类型,在加载的时候实例化。
        INSTANCE;
        public static EnumSingleton getInstance(){
            return INSTANCE;
        }
    }

    优点:仅实例化一次,线程是安全的。获取实例的速度快

    缺点:类加载时立即实例化对象,可能实例化的对象不被使用,造成内存的浪费。
     
     

    六、枚举和懒汉模式相结合

    public class EnumSingletonDemo {
     
        private enum EnumHolder{
            INSTANCE;
            private static  EnumSingletonDemo instance=null;
      
            private EnumSingletonDemo getInstance(){
                if(instance ==null) {
                    instance = new EnumSingletonDemo();
                }
                return instance;
            }
        }
      
        //实现懒加载
        public static EnumSingletonDemo  getInstance(){
            return EnumHolder.INSTANCE.getInstance();
        }

    优点:1、线程安全。且不用加锁。

              2、实现了懒加载
    缺点:仍然需要实例非空判断,耗费一定资源
     
     
     
     
  • 相关阅读:
    flume 使用遇到问题及解决
    定时任务 Linux cron job 初步使用
    java instrumentation &JVMTI
    Java远程执行Shell命令
    No input clusters found in output/ZS_TEST_OUTPUT3404268420/clusters-0/part-randomSeed. Check your -c argument.
    asp.net core 中读取post 方式来的内容
    C#程序 权限不够的解决方案
    wamp下安装https 实现 ssl 协议,主要是编写小程序通讯
    如何让thinkpad X1C 用U盘 安装上专业版win10
    php 5.4 5.5 如何连接 ms sqlserver
  • 原文地址:https://www.cnblogs.com/LemonFive/p/11149034.html
Copyright © 2011-2022 走看看