本文共 3085 字,大约阅读时间需要 10 分钟。
ThreadLocal是线程私有变量,本身是解决多线程环境线程安全,可以说单线程实际上没必要使用。
既然多线程环境本身不使用static,那么又怎么会线程不安全。所以这个问题本身并不是问题,只是有人没有理解ThreadLocal的真正使用场景,所以有此疑问。
看看jdk源码推荐ThreadLocal使用static吧:
/** * This class provides thread-local variables. These variables differ from * their normal counterparts in that each thread that accesses one (via its * {@code get} or {@code set} method) has its own, independently initialized * copy of the variable. {@code ThreadLocal} instances are typically private * static fields in classes that wish to associate state with a thread (e.g., * a user ID or Transaction ID). * *For example, the class below generates unique identifiers local to each * thread. * A thread's id is assigned the first time it invokes {@code ThreadId.get()} * and remains unchanged on subsequent calls. *
* import java.util.concurrent.atomic.AtomicInteger; * * public class ThreadId { * // Atomic integer containing the next thread ID to be assigned * private static final AtomicInteger nextId = new AtomicInteger(0); * * // Thread local variable containing each thread's ID * private static final ThreadLocal<Integer> threadId = * new ThreadLocal<Integer>() { * @Override protected Integer initialValue() { * return nextId.getAndIncrement(); * } * }; * * // Returns the current thread's unique ID, assigning it if necessary * public static int get() { * return threadId.get(); * } * } **Each thread holds an implicit reference to its copy of a thread-local * variable as long as the thread is alive and the {@code ThreadLocal} * instance is accessible; after a thread goes away, all of its copies of * thread-local instances are subject to garbage collection (unless other * references to these copies exist). * * @author Josh Bloch and Doug Lea * @since 1.2 */public class ThreadLocal
{ /** * ThreadLocals rely on per-thread linear-probe hash maps attached * to each thread (Thread.threadLocals and * inheritableThreadLocals). The ThreadLocal objects act as keys, * searched via threadLocalHashCode. This is a custom hash code * (useful only within ThreadLocalMaps) that eliminates collisions * in the common case where consecutively constructed ThreadLocals * are used by the same threads, while remaining well-behaved in * less common cases. */
这个是Josh Bloch和Doug Lea写的,再看看他们的著作:《Java并发编程实战》
再看看jdk中的官方文档:
已经说的很明白了,再看看其他答案吧:
按照类的定义
此类提供线程局部变量。这些变量与普通变量不同,每个访问一个线程(通过其get或set方法)的线程都有其自己的,独立初始化的变量副本。ThreadLocal实例通常是希望将状态与线程关联的类中的私有静态字段(例如,用户ID或事务ID)。
这意味着说2个线程t1
并t2
执行someBMethod()
,它们分别结束设置x1
&x2
(的实例X
)。现在,当t1
come并执行时,someCMethod()
它会获取x1
(它是由它自己设置的)和gets 。t2
x2
换句话说,只有一个静态实例是安全的ThreadLocal
,因为在内部调用时它会执行类似的操作set
Java 源代码,
-
java.lang.Thread Class
包含一个实例变量,如下所示。ThreadLocal.ThreadLocalMap threadLocals = null;
因为threadLocals
变量是非静态的,所以应用程序中的每个线程(即Thread Class的每个实例)将拥有它自己的threadLocals映射副本。
-
该映射的键是当前 ThreadLocal实例,而value是您作为参数传递给ThreadLocal.set()的值。
-
当您尝试在内部获取 as值时
ThreadLocal.get()
,它将从Current Thread的ThreadLocalMap获取。
简而言之,您是从当前线程对象获取&设置值,而不是从ThreadLocal对象获取&设置值。
转载地址:https://linuxstyle.blog.csdn.net/article/details/105021557 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!