浅谈volatile

初学Java,最近总是碰到volatile关键字,下面说说自己的见解

volatile关键字主要有一下特性:

1.保证原子性;2.实现可见性;3.防止重排序;

1.在声明变量时,使用volatile关键字可以保证这个变量的原子性,保证了每次读/写时只会读到确定的数据。

        例如普通的double和float类型都不保证原子性的,在读取这两种数据类型时,会先读取前32位,若此时此数据发生改变,

则数据是不安全的,可以使用volatile关键字;

2.可见性主要体现在多线程方面,当一个线程修改了某变量的值时,另一个线程没有看到,其原因是每个线程都有一个高速缓冲区,使用volatile则可保证每个线程读到同样的数据;

3.在声明一个变量时,JVM实例化一个对象可分为3步:

  (1)分配内存空间;

  (2)初始化对象;

  (3)将内存空间的地址赋值给对应的引用;

而其中,第2,3步是可以改变顺序的,这样,在多线程环境下,这个弊端就暴露出来了,在重排序时可能会读到null值,接下来我们来看一个单例:

public class Singleton { 
  private volatile static boolean flag;
  /* 私有构造方法,防止被实例化 */ 
  private Singleton() { 
    if(!flag){
      flag = false;
    }else{
      throw new RuntimeException("不能多次创建单例对象");
    }
  }

  /* 此处使用一个内部类来维护单例 */ 
  private static class SingletonFactory { 
    private static Singleton instance = new Singleton();
  }

  /* 获取实例 */ 
  public static Singleton getInstance() { 
    return SingletonFactory.instance; 
  }

  /* 如果该对象被用于序列化,可以保证对象在序列化前后保持一致 */ 
  private Object readResolve() { 
    return getInstance(); 
  } 
}

这里使用volatile关键字就是为了在JVM中只创建一个单例对象,保证了对象的原子性,可见性,防止重排序。

posted @ 2017-11-03 09:52  xlzpx  阅读(264)  评论(0编辑  收藏  举报