ThreadLocal

ThreadLocal不能保证其创建的对象是全局唯一,但能保证在单个线程中是唯一的。

示例:

package com.example.springbootdemo.singleton;

public class ThreadLocalSingleton {
    private static final ThreadLocal<ThreadLocalSingleton> threadLocalInstance =
            new ThreadLocal<ThreadLocalSingleton>(){
                @Override
                protected ThreadLocalSingleton initialValue() {
                    return new ThreadLocalSingleton();
                }
            };
    private ThreadLocalSingleton(){}
    public static ThreadLocalSingleton getInstance(){
        return threadLocalInstance.get();
    }

    public static void main(String[] args) {
        System.out.println(ThreadLocalSingleton.getInstance());
        System.out.println(ThreadLocalSingleton.getInstance());
        System.out.println(ThreadLocalSingleton.getInstance());
        System.out.println(ThreadLocalSingleton.getInstance());
        System.out.println(ThreadLocalSingleton.getInstance());
    }
}

 

当使用ThreadLocal维护变量时,ThreadLocal为每个使用该变量的线程提供独立的变量副本,所以每一个线程都可以独立地改变自己的副本,而不会影响其它线程所对应的副本。

ThreadLocal是如何做到为每一个线程维护变量的副本的呢?

  每个线程中都有一个独立的ThreadLocalMap,它所存储的值,只能被当前线程读取和修改

源代码:

 

public void set(T value) {
        Thread t = Thread.currentThread();  //拿到当前线程
        ThreadLocalMap map = getMap(t);     //拿到当前线程里的ThreadLocalMap
        if (map != null)
            map.set(this, value);           //键值为当前ThreadLocal对象,值为要维护的变量
        else
            createMap(t, value);
    }

 

getMap(t)是怎么来的呢? 源码 : 
 ThreadLocalMap getMap(Thread t) {
        return t.threadLocals;
    }

 

t.threadLocals是啥?
参见Thread类: 原来Thread类有个threadLocals成员变量
 /* ThreadLocal values pertaining to this thread. This map is maintained
     * by the ThreadLocal class. */
    ThreadLocal.ThreadLocalMap threadLocals = null;

ThreadLocal.ThreadLocalMap是啥? 原来ThreadLocal有个静态内部类
 static class ThreadLocalMap

 

 
public T get() {
        Thread t = Thread.currentThread();
        ThreadLocalMap map = getMap(t);
        if (map != null) {
            ThreadLocalMap.Entry e = map.getEntry(this);
            if (e != null) {
                @SuppressWarnings("unchecked")
                T result = (T)e.value;
                return result;
            }
        }
        return setInitialValue();
    }

 

ThreadLocal和传统的synchronized有啥区别?

synchronized是锁机制进行时间换空间,ThreadLocal是存储拷贝进行空间换时间。

posted @ 2019-01-25 17:50  Emyin  阅读(132)  评论(0编辑  收藏  举报