首先线程之间是隔离的,那么什么时候才会出现线程安全问题?
三个字:同时 写; 打比方如下: //双重检验懒汉式单例模式; public class Lanhanshishuangchong {
private static Lanhanshishuangchong lanhanshishuangchong; private Lanhanshishuangchong(){ } public static Lanhanshishuangchong getLanhanshishuangchong(){ if(lanhanshishuangchong==null){ synchronized (Lanhanshishuangchong.class) { if(lanhanshishuangchong==null) { Lanhanshishuangchong lanhanshishuangchong = new Lanhanshishuangchong(); } } } return lanhanshishuangchong; }}
}
这是普通的懒汉式单例模式。 public class Lanhanshishuangchong {
private static Lanhanshishuangchong lanhanshishuangchong; private Lanhanshishuangchong(){ } public static Lanhanshishuangchong getLanhanshishuangchong(){ if(lanhanshishuangchong==null){ Lanhanshishuangchong lanhanshishuangchong = new Lanhanshishuangchong(); } return lanhanshishuangchong; }if(lanhanshishuangchong==null){
Lanhanshishuangchong lanhanshishuangchong = new Lanhanshishuangchong();//双重检验懒汉式单例模式; public class Lanhanshishuangchong {
private static Lanhanshishuangchong lanhanshishuangchong; private Lanhanshishuangchong(){ } public static Lanhanshishuangchong getLanhanshishuangchong(){ if(lanhanshishuangchong==null){ synchronized (Lanhanshishuangchong.class) { if(lanhanshishuangchong==null) { Lanhanshishuangchong lanhanshishuangchong = new Lanhanshishuangchong(); } } } return lanhanshishuangchong; }}
}
怎么解决的呢?
啥话不说肯定先加锁么。
synchronized (Lanhanshishuangchong.class)
加了锁 就结束了吗?
你以为加了锁就只能一个线程进去,然后第二个线程进来的时候就直接用上面创建的对象吗?
你以为的你以为不是你以为的。
为什么?
你永远要知道有可能发生的事情,在程序中。第一个线程创建了对象,他就一直存在吗?
如果啊两个线程几乎同时访问,那么是有可能线程安全的,否则,第一个都被回收了,这个时候在进来的时候,还是空的,就得还去创建,那么还是会去new,那么两次new的对象就不是一个 对象了。对象地址改变,那么就违背单利的原则,造成线程不安全。
只有再加上 if(lanhanshishuangchong==null) ,才能解决这个问题。