ThreadLocal
文章目录
1.ThreadLocal的作用
通常情况下,我们创建的变量可以被任何一个线程访问并修改,但是在多线程运行的环境下,我们希望每一个线程都有自己的本地专属变量,该怎么实现呐?(例如每个线程都保存该线程独有的 UserId 、TranactionId)
类似于JVM中分配内存,所有线程共享的Java堆中可以划分出多个线程私有的分配缓冲区TLAB(Thread Local Allocation Buffer),提升对象分配的效率
Java的JDK提供了一个解决方案: ThreadLocal
2.ThreadLocal的使用
Web应用程序就是典型的多任务引用,Java提供线程池可以方便执行这些请求任务并复用线程;
每个用户的请求,都会创建一个任务 Runnable
Runnable task = ()->{
public void UserPorcess(User user){
checkPermisson();
loadResouce();
doWork();
saveStatus();
sendResponse();
}
}
// 放到线程池中运行
executor.execute(task);
传入的用户参数 User user ,如何在一个线程内传递状态?
- 1.将user参数传入到所有方法中
- 2.将user信息保存到本地线程中,需要用户信息执行get()方法获取上来
Context上下文:
在一个线程中,横跨若干个方法调用,需要传递的对象,通常称之为上下文(Context),它是一种状态。
对于第一种方法,将user参数传入所有的方法中,且不论每个方法都增加一个context参数的复杂程度,一旦调用第三方库时,无法修改代码,user参数就无法传入。
TheadLocal就是将信息保存包本地线程中,在一个线程中传递同一个对象
This class provides thread-local variables. These variables differ from
their normal counterparts in that each thread that accesses one (via its
get or set method has its own, independently initialized copy of the variable.
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).
适用场景:
- 每个线程需要有自己单独的实例
- 实例需要在多个方法中共享,但不希望被多线程共享
存储用户session的例子
// 私有静态
private static final ThreadLocal threadSession = new ThreadLocal();
public static Session getSession() throws Exception {
Session s = (Session) threadSession.get(