• 设计模式之————单例模式


    设计模式

    一、单例模式

    1. 什么是单例模式?

    单例模式,指的就是在整个软件系统的生命周期中,某个类的对象至始至终只有一个对象。

    创建单例模式的方法有很多种,下面一一分析:

    2. 饿汉式

    package com.pattern.design.singleton.type1;
    
    /**
     * @author dingding
     *
     */
    public class SingletonTest1 {
    	
    	public static void main(String[] args) {
    		Singleton singleton = Singleton.getInstance();
    		Singleton singleton2 = Singleton.getInstance();
    		System.out.println(singleton == singleton2);
    		System.out.println(singleton.hashCode() == singleton2.hashCode());
    	}
    
    }
    
    // 恶汉式,静态变量
    // 在类加载的同时就创建实例,保证了线程的安全
    // 缺点:如果类对象一直未使用,会造成内存的浪费
    
    class Singleton {
    
    	// 1.私有化构造方法
    	private Singleton() {
    
    	}
    
    	// 2.本类内部构造对象实例
    	private static final Singleton singleton = new Singleton();
    
    	// 3.对外提供一个公有的静态方法,返回实例对象
    	public static Singleton getInstance() {
    		return singleton;
    	}
    
    }
    

    3. 饿汉式(静态代码块)

    package com.pattern.design.singleton.type2;
    
    /**
     * @author dingding
     *
     */
    public class SingletonTest2 {
    	
    	public static void main(String[] args) {
    		Singleton singleton = Singleton.getInstance();
    		Singleton singleton2 = Singleton.getInstance();
    		System.out.println(singleton == singleton2);
    		System.out.println(singleton.hashCode() == singleton2.hashCode());
    	}
    
    }
    
    // 恶汉式,代码块中构造对象实例
    // 在类加载的同时就创建实例,保证了线程的安全
    // 缺点:如果类对象一直未使用,会造成内存的浪费
    
    class Singleton {
    
    	// 1.私有化构造方法
    	private Singleton() {
    
    	}
    	
    	private static Singleton singleton = null;
    
    	// 2.代码块中构造对象实例
    	static{
    		singleton = new Singleton();
    	}
    
    	// 3.对外提供一个公有的静态方法,返回实例对象
    	public static Singleton getInstance() {
    		return singleton;
    	}
    
    }
    

    4. 懒汉式(线程不安全)

    package com.pattern.design.singleton.type2;
    
    /**
     * @author dingding
     *
     */
    public class SingletonTest2 {
    	
    	public static void main(String[] args) {
    		Singleton singleton = Singleton.getInstance();
    		Singleton singleton2 = Singleton.getInstance();
    		System.out.println(singleton == singleton2);
    		System.out.println(singleton.hashCode() == singleton2.hashCode());
    	}
    
    }
    
    // 恶汉式,代码块中构造对象实例
    // 在类加载的同时就创建实例,保证了线程的安全
    // 缺点:如果类对象一直未使用,会造成内存的浪费
    
    class Singleton {
    
    	// 1.私有化构造方法
    	private Singleton() {
    
    	}
    	
    	private static Singleton singleton = null;
    
    	// 2.代码块中构造对象实例
    	static{
    		singleton = new Singleton();
    	}
    
    	// 3.对外提供一个公有的静态方法,返回实例对象
    	public static Singleton getInstance() {
    		return singleton;
    	}
    
    }	
    

    5. 懒汉式(线程安全,同步方法)

    package com.pattern.design.singleton.type4;
    
    /**
     * @author hp
     *
     */
    public class SingletonTest4 {
    
    }
    
    
    // 懒汉式,线程安全
    // 缺点:getInstance方法加了锁,在多线程场景中,需要等待,效率不高
    class Singleton {
    	private static Singleton single;
    
    	private Singleton() {
    
    	}
    
    	public static synchronized Singleton getInstance() {
    		if (single == null) {
    			single = new Singleton();
    		}
    		return single;
    	}
    
    }
    

    6. 懒汉式(同步代码块,线程不安全)

    package com.pattern.design.singleton.type5;
    
    /**
     * @author hp
     *
     */
    public class SingletonTest5 {
    
    }
    
    // 懒汉式,同步代码块
    // 缺点:该方法和方法4一样,并没有能解决线程安全的问题
    class Singleton {
    	private static Singleton singleton;
    
    	private Singleton() {
    
    	}
    
    	public static Singleton getInstance() {
    		if (singleton == null) {
    			synchronized (Singleton.class) {
    				singleton = new Singleton();
    			}
    		}
    		return singleton;
    	}
    
    }
    

    7. 懒汉式(双重检查,线程安全,推荐)

    public class SingletonTest6 {
    
    }
    
    // 双重检查
    // 解决了线程安全性、懒加载问题,推荐使用
    
    class Singleton {
    	private static volatile Singleton singleton;
    
    	private Singleton() {
    
    	}
    
    	public static Singleton getInstance() {
    		if (singleton == null) {
    			synchronized (Singleton.class) {
    				if (singleton == null) {
    					singleton = new Singleton();
    				}
    			}
    		}
    		return singleton;
    	}
    }
    

    8. 懒汉式(静态内部类,安全,推荐)

    package com.pattern.design.singleton.type7;
    
    /**
     * @author hp
     *
     */
    public class SingletonTest7 {
    
    }
    
    //懒汉式(静态变量)
    //外部类加载时,不会加载内部类;调用getInstance方法时,会加载内部类
    //推荐使用,解决了懒加载和线程安全的问题
    
    class Singleton {
    	private Singleton() {
    
    	}
    
    	private static class SingletonInstance {
    		private static final Singleton INSTANCE = new Singleton();
    	}
    
    	public static Singleton getInstance() {
    		return SingletonInstance.INSTANCE;
    	}
    
    }
    

    9. 枚举式(线程安全,推荐)

    package com.pattern.design.singleton.type8;
    
    /**
     * @author hp
     *
     */
    public class SingletonTest8 {
    
    	public static void main(String[] args) {
    		Singleton singleton = Singleton.INSTANCE;
    		Singleton singleton2 = Singleton.INSTANCE;
    		
    		System.out.println(singleton == singleton2);
    		System.out.println(singleton.hashCode() == singleton2.hashCode());
    	}
    	
    }
    
    /**
     * 
     * 枚举类型实现单例模式
     * 优点:不仅可以避免多线程的同步问题,而且可以防止反序列化创新创建新的对象
     * 		推荐使用
     */
    enum Singleton{
    	INSTANCE;
    }
    
  • 相关阅读:
    455. Assign Cookies(分饼干)(leetcode)
    栈的压入、弹出序列 (剑指offer)
    第五届蓝桥杯c/c++B组1
    第六届蓝桥杯试题c/c++B组8
    第六届蓝桥杯试题c/c++B组7
    第六届蓝桥杯试题c/c++B组6
    第六届蓝桥杯试题c/c++B组5
    第六届蓝桥杯试题c/c++B组4
    第六届蓝桥杯试题c/c++B组3
    第六届蓝桥杯试题c/c++B组2
  • 原文地址:https://www.cnblogs.com/lfdingye/p/11605326.html
Copyright © 2020-2023  润新知