2

下面是创建线程局部变量的示例

private static final ThreadLocal<SimpleDateFormat> formatter = new ThreadLocal<SimpleDateFormat>(){
    @Override
    protected SimpleDateFormat initialValue()
    {
        return new SimpleDateFormat("yyyyMMdd HHmm");
    }
};

还有第二种使用线程本地的方法

public class MyThreadLocal {

    public static final ThreadLocal userThreadLocal = new ThreadLocal();

    public static void set(Context user) {
        userThreadLocal.set(user);
    }

    public static void unset() {
        userThreadLocal.remove();
    }

    public static Context get() {
        return userThreadLocal.get();
    }
}

现在,下面的行创建了一个线程局部变量,它是静态的。

public static final ThreadLocal userThreadLocal = new ThreadLocal();

每当在 JVM 中加载类时,都会初始化静态变量。这意味着当类加载时创建一个对象。

* *问题:*当不同的线程调用 ThreadLocal 变量上的 Set 或 get 时,threadlocal 对象的副本是如何传递给线程的?*每个线程如何获取自己的对象? 如果在加载类时创建了一个对象,那么这是怎么回事?**

4

2 回答 2

3

这实际上是 Thread 实现的一部分。

原则上,您可以认为每个 Thread 实例都有一个 Map,其中 ThreadLocal 对象实例(只有一个)是,与之关联的值是值。

ThreadLocal 的静态实例根本不保存值,它只是一个标记,供 Thread 再次查找它(Thread 存储值)。

所以

userThreadLocal.get();

是这样的

currentThread.privateMapOfThreadLocalValues.get(userThreadLocal);      
于 2013-09-20T08:32:51.567 回答
1

我认为ThreadLocal的文档中清楚地描述了答案

总结一下,我引用

此类提供线程局部变量。这些变量不同于它们的正常对应变量,因为每个访问一个(通过它的 get 或 set 方法)的线程都有它自己的、独立初始化的变量副本。ThreadLocal 实例通常是希望将状态与线程相关联的类中的私有静态字段(例如,用户 ID 或事务 ID)。

只要线程处于活动状态并且 ThreadLocal 实例可访问,每个线程都持有对其线程局部变量副本的隐式引用;在线程消失后,它的所有线程本地实例副本都将受到垃圾回收(除非存在对这些副本的其他引用)。

希望这可以澄清。

于 2013-09-20T08:37:30.703 回答