ThreadLocal principle resolved with source code

ThreadLocal can be used to store thread-local variables ThreadLocal variables can only be created by the current thread access, other threads can not modify. Isolated from each other between the thread to read and write.

 

First, the principle resolved

. 1, in the presence of a class ThreadLocal ThreadLocalMap subclass, and achieve similar HashMap, ThreadLocalMap bond is a weak reference of ThreadLocal.

Weak references: when all strong references to the ThreadLocal objects are not, weak references will be directly recovered at the next GC.

ThreadLocalMap achieve the following subclasses of FIG.

 

 

 

 

 

 

 

 

 

 

 

 

 

2, see the source ThreadLocal class set method, the source code as shown in FIG.

1) to obtain the current thread.

2) obtain ThreadLocal.ThreadLocalMap threadLocals variable current thread, the variable is the Thread class member variables.

3) ThreadLocalMap variable If the thread is not empty, direct assignment.

4) If the variable is empty ThreadLocalMap threads, call new ThreadLocalMap (this, firstValue) ThreadLocalMap to initialize the object, and the current passing through the corresponding ThreadLocal instance constructor.

3, see the source ThreadLocal class get method, relatively simple logic, not with source code.

1) Get the current thread.

2) obtain ThreadLocalMap variable current corresponding to the thread.

3) Get Entry corresponding to the current ThreadLocal instance by ThreadLocalMap, then acquires the corresponding value.

4, when a thread has more ThreadLocal variables, how to achieve each ThreadLocal is not affected, the situation does not appear to cover each other.

private final int threadLocalHashCode = nextHashCode();

private static AtomicInteger nextHashCode = new AtomicInteger();

private static final int HASH_INCREMENT = 0x61c88647;

private static int nextHashCode() {
     return nextHashCode.getAndAdd(HASH_INCREMENT);
}

We can see, ThreadLocal internal maintains a constant static hashcode values, each ThreadLocal uniquely corresponds to a hashcode value, ensure that when the map is set / get operation, the situation will not be covered.

 

Second, note the use of ThreadLocal

By Source understand ThreadLocal source code to implement, but can not just stay on the surface, we need to go into why the source code so achieve and where there is need to pay attention to use.

In the daily development, the following questions need.

1, ThreadLocalMap Why maintain a ThreadLocal weak references? What memory leak root reason is?

Reference relationship shown below:

It should be noted a premise: if a thread of life cycle is very long.

First of all, if we maintain a strong reference, must be unreasonable, it will cause a memory leak. Maintains a weak reference, when ThreadLocal be recovered GC, ThreadLocalMap the keys will be gone with the wind, there will be a lot of key situations for the null value is not null, it will cause some memory leaks.

Until after the demise of the thread, ThreadLocalMap thread will eventually be recovered.

When the JVM optimized in this regard, calls the set, get, remove method, the key will be null clean up the map.

The root cause of memory leaks is the thread of the life cycle is very long, because soon die out if the thread, the thread will ThreadLocalMap to clean up the memory leak does not occur.

2, using the following matters thread pool strategy.

Thread pool policy enforcement, some threads will repeat the task. Imagine if before the end of the run method of execution, not ThreadLocal to clean up, will cause the situation to cover the value of the ThreadLocal appears, can cause abnormal operations.

所以,在线程池的策略下使用ThreadLocal,需要像lock进行加锁和解锁一样,finally里面对ThreadLocal进行remove。

3、子线程如何使用父线程的ThreadLocal变量?

可以使用InheritableThreadLocal。

通过看Thread的源码发现:

/*
* InheritableThreadLocal values pertaining to this thread. This map is
* maintained by the InheritableThreadLocal class.
*/
ThreadLocal.ThreadLocalMap inheritableThreadLocals = null;

InheritableThreadLocal<T> extends ThreadLocal<T>

InheritableThreadLocal继承了ThreadLocal类,重写了getMap和createMap。操作的是线程的inheritableThreadLocals 变量。

再通过查看Thread的构造方法,可以发现,会对父线程的ThreadLocal变量进行复制,并将值赋给inheritableThreadLocals

 

如有不对之处,欢迎指正!

Guess you like

Origin www.cnblogs.com/zengleisure/p/11283842.html