面试的时候忘记问的是哪家公司了。这不是一个常见的问题。我当时没有正确回答。我是按照线程通信集来的,比如XJB说的synchronized、Locks、volatile。面试找了一些资料,今天整理出来分享给大家~ThreadLocal的具体原理本文就不多说了。每个人都可以记住他们能做的一切。其实有两点:链接透传(一般情况下方便传参),调用方法时不需要携带一堆请求参数)线程隔离每个线程都有自己的ThreadLocalMap,持有的数据通过ThreadLocal存储在这个Map(Thread.ThreadLocalMapthreadLocals)中,所以可以实现线程隔离。毕竟每个线程的ThreadLocalMap都是不一样的,那么如果子线程想获取父线程中的ThreadLocal值怎么办呢?比如会有下面代码的实现。在子线程中调用get的时候,我们得到的Thread对象就是当前的子线程对象,对吧?每个线程都有自己独立的ThreadLocal,所以当前子线程的ThreadLocalMap为null(而父线程,也就是main线程中的ThreadLocalMap有数据),所以我们得到的值也是nullpublicclassThreadLocalTest{privatestaticThreadLocalthreadLocal=newThreadLocal();publicstaticvoidmain(String[]args)throwsException{threadLocal.set("Flyingveal");System.out.println("父线程的值:"+threadLocal.get());newThread(newRunnable(){@Overridepublicvoidrun(){System.out.println("子线程的值:"+threadLocal.get());}}).start();线程.睡眠(2000);}}结果输出如下:父线程的值:飞天小牛肉的子线程值:null这个问题怎么解决?我们先从Thread类找思路:你会发现在ThreadLocalMapthreadLocals下,还有一个ThreadLocalMap变量inherittableThreadLocals,inherit翻译为继承。先看这个变量的注释:InheritableThreadLocalvaluespertainedtothisthread。这张图是由InheritableThreadLocal类维护的。oho,这里新增了一个查查辉没体验过的继承类:InheritbleThreadLocal翻译一下注释,大概是,如果使用InheritableThreadLocal,保存的数据不再在原来的ThreadLocal.ThreadLocalMapthreadLocals中,而是在一个新的ThreadLocal.ThreadLocalMapinheritableThreadLocals变量中。所以,如果想要在上面这段代码中,子线程可以获取到父线程的ThreadLocal值,只需要将ThreadLocal语句改为InheritableThreadLocal即可。下面看看InheritableThreadLocal是如何在父子线程之间传递值的。先看线程在newThread时做了什么Thread#init()privatevoidinit(ThreadGroupg,Runnabletarget,Stringname,longstackSize,AccessControlContextacc){//省略一些代码Threadparent=currentThread();if(inheritThreadLocals&&parent.inheritableThreadLocals!=null)//复制父线程的map,新建一个map赋给当前线程的inheritableThreadLocalsthis.inheritableThreadLocals=ThreadLocal.createInheritedMap(parent.inheritableThreadLocals);//省略部分代码}core其实就是上面几行代码。如果设置了inheritableThreadLocals变量,那么Thread会将父线程ThreadLocalthreadLocals中的所有数据复制到子线程的InheritableThreadLocalinheritableThreadLocals中。而且copy调用的createInheritedMap方法其实是一个浅拷贝函数。键和值是原始参考地址。这里所谓的复制,其实就是将一个Map中的数据复制到另一个Map中:至此,InheritableThreadLocal已经大致说明了为什么可以解决父子线程之间传递Threadlcoal值的问题?总结一下:在创建InheritableThreadLocal对象时,将其赋值给线程的t.inheritableThreadLocals变量。创建新线程时,会检查父线程中的t.inheritableThreadLocals变量是否为null。如果不为null,则复制一份数据到子线程的t.inheritableThreadLocals成员变量中。InheritableThreadLocal重写了getMap(Thread)方法,所以在获取的时候,会从t.inheritableThreadLocals中获取ThreadLocalMap对象,这样就可以获取到父线程ThreadLocal中的值。