zoukankan      html  css  js  c++  java
  • 1.单例设计模式

    1.单例设计模式

    a.概述

    • 单例设计模式是指某个类只有一个实例的设计模式。
    • 特点:
        • 1.构造函数是private修饰的,目的是防止用户调用构造函数创建对象
        • 2.类的内部有静态工厂方法,返回该类的唯一实例。
        • 3.类的唯一实例被private staic修饰的引用所修饰    

    b.单例分类

    • 饿汉单例
    • /**
       * Created by yangyun on 2017/2/23.
       */
      public class SingletonTest {
          //饿汉单例在类初始化的时候创建实例
          private static SingletonTest instance=new SingletonTest();
      
          private SingletonTest(){}
      
          public static SingletonTest getInstance(){
              return instance;
          }
      }
      
    • 特点:
        • 优点:天生就是线程安全的,不用进行同步的处理
        • 缺点:类加载的初始化阶段,会把类的staic字段放在clinit函数中进行执行,也就会初始化类的单例,这样做的缺点是无论是否会用到这个单例都会产生这个实例,有时候会浪费空间。
    • 懒汉单例
    • public class SingletonTest {
          //饿汉单例在类初始化的时候创建实例
          private static SingletonTest instance;
      
          private SingletonTest(){}
      
          public synchronized static SingletonTest getInstance(){
              if(instance==null){
                  instance=new SingletonTest();
              }
              return instance;
          } 
      }
    • 特点:
        • 优点:考虑了线程安全,在特定的情况下可以节约内存
        • 缺点:同步会影响效率,整个函数都是同步的,每次调用都需要等待其他线程释放锁
    • 懒汉单例------改进
    • 改进:仅仅同步创建对象的代码块
    • public class SingletonTest {
          //饿汉单例在类初始化的时候创建实例
          private static SingletonTest instance;
      
          private SingletonTest(){}
      
          public static SingletonTest getInstance(){
      
              if(instance==null) {
                  synchronized (SingletonTest.class) {
                      if (instance==null) {
                          instance = new SingletonTest();
                      }
                  }
              }
              return instance;
          }
      }  
    • 为什么两次判断instance==null
    • 假设有两个线程在第一次判断后都为true,线程A先获取了对象锁,创建了对象后释放锁
    • 第二个线程获取锁后,进行第二次instance==null的检查后,避免再次创建对象

    c.反射与单例

    • /**
       * Created by yangyun on 2017/2/23.
       */
      public class SingletonTest {
          //饿汉单例在类初始化的时候创建实例
          private static SingletonTest instance;
      
          private SingletonTest(){}
      
          public static SingletonTest getInstance(){
      
              if(instance==null) {
                  synchronized (SingletonTest.class) {
                      if (instance==null) {
                          instance = new SingletonTest();
                      }
                  }
              }
              return instance;
          }
      
          public static void main(String[] args){
              try {
                  SingletonTest instance1=SingletonTest.class.newInstance();
                  SingletonTest instance2=SingletonTest.getInstance();
                  System.out.println(instance1);
                  System.out.println(instance2);
              } catch (InstantiationException e) {
                  e.printStackTrace();
              } catch (IllegalAccessException e) {
                  e.printStackTrace();
              }
          }
      }//instace1、instance2的地址是不一样的,是两个对象
    • 说明:
    • 通过放射,可以调用类的构造函数,即使是private构造函数也是可以的
    • 所以说在反射面前所有的单例设计模式都是失效的。
  • 相关阅读:
    小程序游戏如何接入支付呢?
    手机回复小程序客服消息
    小程序客服发送卡片消息
    小程序多客服对应售前售后,或者不同的客服人员
    php 7 event 安装
    workerman相关
    树莓派:你是我的眼
    Python应用03 使用PyQT制作视频播放器
    从写博到出书:过程全记录
    协议森林17 我和你的悄悄话 (SSL/TLS协议)
  • 原文地址:https://www.cnblogs.com/yangyunnb/p/6432835.html
Copyright © 2011-2022 走看看