ThreadLocal 是什么?
ThreadLocal是一个线程内部数据的存储类,通过它可以在指定的线程中存储数据,数据存储之后,只有在指定线程中可以获得到存储的数据,对于其他线程来说则无法获取到数据。
下面通过一个例子来了解ThreadLocal对象:
public class ThreadLocalTest {
private static ThreadLocal<Integer> t = new ThreadLocal<Integer>();
public static void main(String[] args) {
t.set(8);
System.out.println(Thread.currentThread().getName()+t.get());
new Thread(){
@Override
public void run(){
t.set(5);
System.out.println(Thread.currentThread().getName()+t.get());
}
}.start();
new Thread(){
@Override
public void run(){
t.set(7);
System.out.println(Thread.currentThread().getName()+t.get());
}
}.start();
}
}
结果如下:
由结果可以看出:主线程,线程0,线程1,虽然访问的是同一个对象的值,但是每个线程获得的值是不一样的。这是因为不同的线程访问的是同一个ThreadLocal对象的get()方法,ThreadLocal内部会从各自的线程中取出一个数组,然后再从数组中根据当前ThreadLocal的索引去查出对应的value值,不同线程中数组不同。所以可以在不同线程中有不同的副本,而且互不干扰。
public class ThreadLocal<T> {}
主要有4个方法,主要理解set()和get()方法就可以理解它的工作原理了
下面看下set()的源码:
我们可以知道set()是通过values来取得当前线程的ThreadLocal的值。public void set(T value) { Thread currentThread = Thread.currentThread(); Values values = values(currentThread); if (values == null) { values = initializeValues(currentThread); } values.put(this, value); }
get()的源码如下:
public T get() { // Optimized for the fast path. Thread currentThread = Thread.currentThread(); Values values = values(currentThread); if (values != null) { Object[] table = values.table; int index = hash & values.mask; if (this.reference == table[index]) { return (T) table[index + 1]; } } else { values = initializeValues(currentThread); } return (T) values.getAfterMiss(this); }
我们可以看出get()方法是取出当前线程的ThreadLocal的值,如果为空就返回null