Bootstrap

线程的局部变量——ThreadLocal

ThreadLocal是什么

对这个词语分解,将其分为Thread和Local,顾名思义便是本线程的变量,既然是当前线程的变量,那么就意味着这个变量对于其他线程来说就是隔离的,也就是不可见的,ThreadLocal对每一个线程都有一个副本,以确保每一个线程都能且只能访问自己线程内部的副本变量

ThreadLocal如何实现

听起来这个ThreadLocal是不是也是比较容易懂的,那么吗,ThreadLocal又是怎么实现的呢?
在最早期,ThreadLocal的实现方式就是利用类内部的一个线程安全的Map,这个Map的键是线程的ID,值是实例的对象。这样就使得线程之间互不干扰,能起到隔离的效果,但这样做会有一个缺点:
多线程的情况之下,多个线程会竞争同一个map的键,竞争产生了,那么就得进行加锁处理,这样会耗费比较多的资源,除此之外,这种方式也可能造成内存的泄露问题。
而为了解决这些缺点,我们可以有另一种方式实现ThreadLocal,可以简单的理解为上述方式“反过来”,线程对象内部存放一个Map,而以ThreadLocal作为Map的键。这样的话就能避免竞争问题,而这样,每个线程访问的都是自己内部的map,这也是现在的ThreadLocal使用的实现方式。

ThreadLocal举例

先举一个简单的例子吧,这样能使后面的源码分析起来更加轻松一点
ThreadLocal既然是线程变量,那自然,在单线程的程序中是没有什么用处的,举一个多线程的例子:

package com.hhw;

public class ThreadLocalDemo {
   
    public static void main(String[] args) {
   
        final ThreadLocalT th = new ThreadLocalT();
        Thread t1 = new Thread("t1"){
   
            @Override
            public void run(){
   
                th.set();
                System.out.println(th.get());
            }
        };
        Thread t2 = new Thread("t2"
;