ThreadLocal set() then immediately get() 并不总是取值

ThreadLocal set() then immediately get() doesn't always pick up the value

我无法可靠地获取刚刚设置的 ThreadLocal 值。我试图构建一个简单的例子来说明这个问题:

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;

public class WhosebugQuestion {

    private static ThreadLocal<String> threadLocal;

    public static void main(String[] args) throws Exception {
        ExecutorService threadPool = Executors.newFixedThreadPool(5);
        for (int i = 0; i < 10; i++) {
            threadPool.execute(() -> {
                threadLocal = new ThreadLocal<>();
                threadLocal.set("foo");
                System.out.println(threadLocal.get());
            });
        }
        threadPool.shutdown();
        threadPool.awaitTermination(10, TimeUnit.SECONDS);
    }
}

输出为:

null
foo
foo
foo
foo
foo
foo
null
foo
foo

null 值的位置每次都不同。我本以为他们都是 foo。为什么我不能设置 threadLocal 然后立即读取我刚刚设置的值?它是在文档中的某处说的还是 JVM 错误?如果相关,我在 Windows.

上使用 Oracle Java JRE 1.8.0_172

您正在重复创建新的 ThreadLocal

您可以想象 ThreadLocalMap 一样工作,以当前线程作为键。代码可能导致:

threadLocal = new ThreadLocal<>(); ----> one thread create an empty ThreadLocal
threadLocal.set("foo");
System.out.println(threadLocal.get()); ----> another thread get null

您可以将其更改为:

threadPool.execute(() -> {
    threadLocal.set("foo");
    System.out.println(threadLocal.get());
});