并发编程---线程封闭(栈封闭和ThreadLocal)

    在多线程环境中,如果多个线程同时访问一个共同的可变变量,我们称这个变量为共享变量,如果不做任何措施,很可能会引起线程安全问题。那么如何解决这个线程安全问题是我们要考虑的。我们通常的做法是使用同步,但是我们有没有想过线程的安全问题是因为共享,那如果在某些场景下我们不共享数据呢?

    首先我们想到的是如果仅在单线程下访问数据,就不需要同步,这种技术被称为线程封闭。它是实现线程安全的最简单的方法。当某些对象或数据被封闭在一个线程中时,这种做法会自动实现线程安全性,就算被封闭的对象本身并不是线程安全的,但由于是在单线程内部访问,所以它也变成了线程安全的了。

    栈封闭

    当我们在写一个方法的时候,在方法内部定义了一些局部变量,我们根据我们所谓的经验知道这些局部变量是线程安全的。但是为什么这些局部变量是线程安全的呢? 我们先来了解下Jvm运行时内存的一块区域---Java虚拟机栈。我们通常所说的“”就是指的Java虚拟机栈,或者说是虚拟机栈中局部变量表部分。首先Java虚拟机栈是私有的,它的生命周期和线程相同。Java虚拟机栈描述的Java方法执行的内存模型每个方法在执行时都会创建一个“栈帧”,用于存储局部变量表、操作数栈、动态链接、方法出口等信息。每一个方法从调用直至执行完成的过程,就对应这个一个栈帧在虚拟机中入栈到出栈的过程

     我们回到刚才那个问题,为什么局部变量是线程安全的呢?因为局部变量存放在虚拟机栈中,而虚拟机栈是线程私有的,既然线程不共享,所以它是线程安全的。封闭栈的线程安全性体现在Java虚拟机的内存特性。

    ThreadLocal类

    ThreadLocal也提供了线程封闭的特性,简单的理解就是它给每个线程都提供了一个存放线程私有变量的的区域(ThreadLocalMap),这个区域是线程私有的,ThreadLocal提供了get和set等方法来操作这些变量,get总是返回由当前线程在调用get时设置的最新值。 那么ThreadLocal是如何来实现这种机制的呢?

    
   

猜你喜欢

转载自my.oschina.net/u/3765527/blog/1830061