设计模式-创建型模式-单例

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/tangyaliang11/article/details/79833310

单例模式保证一个类只有一个对象,并且提供一个访问该实例的全局访问点。

1.单例模式实例一(饿汉式)

public class Singleton {
	private static Singleton sin = new Singleton(); /// 直接初始化一个实例对象
	private Singleton() { /// private类型的构造函数,保证其他类对象不能直接new一该对象的实例
	}
	public static Singleton getSin() { /// 该类唯一的一个public方法
		return sin;
	}
}

上述代码中的一个缺点是该类加载的时候就会直接new 一个静态对象出来,当系统中这样的类较多时,会使得启动速度变慢。现在流行的设计都是讲延迟加载,我们可以在第一次使用的时候才初始化第一个该类对象。 

2单例模式实例二(懒汉式)

public class Singleton {
	private static Singleton instance;
	private Singleton() {
	}
	public static synchronized Singleton getInstance() { // 对获取实例的方法进行同步
		if (instance == null)
			instance = new Singleton();
		return instance;
	}
}

3单例模式实例三(双重同步锁,不推荐可能有问题)

public class Singleton {  
    private static Singleton instance;  
    private Singleton (){
    }   
    public static Singleton getInstance(){    //对获取实例的方法进行同步
      if (instance == null){
         synchronized(Singleton.class){
             if (instance == null)
                 instance = new Singleton(); 
     }
     }
     return instance;
   }
}

这里面的疑问可能是为什么要做两次判断和锁定Singleton.class
问题一:两个线程同时访问,当线程A的线程B同时访问,都获得instancenull,只有一个线程可以锁定Singleton.class,假设A执行完毕,获得对象,B被唤醒在进行访问时不判断一次,那么就new 出了一个新对象。
问题二:因为是静态方法,所以它只有class可以锁定,没有this锁定。

4.单例模式实例四(使用静态内部类)

public class Singleton {
	private Singleton() {
	}
	public static Singleton getInstance() {
		return Inner.s;
	}
	private static class Inner{
		static Singleton s = new Singleton();
	}
}

你可能认为这与第一种相同,焦点在于是不是延迟加载,静态内部类对于外部成员只有在第一次调用时才被加载。

破解单例模式(不能破解枚举单例)

单例模式可以通过反射或反序列化进行破解
举例代码如下

Class clazz = (Class) Class.forName("com.singleton.Singleton");
Constructor<Singleton> con = clazz.getDeclaredConstructor(null);
con.setAccessible(true);//跳过权限检查
Singleton s = con.newInstance(null);
System.out.println(s);





猜你喜欢

转载自blog.csdn.net/tangyaliang11/article/details/79833310