武义县建设局网站首页,做海报哪个网站的素材多,设计理念怎么写模板,网站建设所用的工具ThreadLocal是什么#xff1f;
ThreadLocal是线程本地存储机制#xff0c;可以将数据缓存在线程内部。ThreadLocal存储的变量在线程内共享的#xff0c;在线程间又是隔离的。
ThreadLocal实现原理#xff1f;
ThreadLocal的底层是ThreadLocalMap#xff0c;每个Thread都…
ThreadLocal是什么
ThreadLocal是线程本地存储机制可以将数据缓存在线程内部。ThreadLocal存储的变量在线程内共享的在线程间又是隔离的。
ThreadLocal实现原理
ThreadLocal的底层是ThreadLocalMap每个Thread都有一个ThreadLocalMap。 ThreadLocalMap存储的键值对key就是ThreadLocal实例value就是要缓存的值。 当创建ThreadLocalset数据时调用的是ThreadLocalMap的set方法set方法将ThreadLocal对象和缓存值存入Map。也就是说想要存入的ThreadLocal中的数据实际上并没有存到ThreadLocal对象中去而是以这个ThreadLocal实例作为key存到了当前线程中的ThreadLocalMap中去了获取ThreadLocal的值时同样也是这个道理。这也就是为什么ThreadLocal可以实现线程之间隔离的原因了。
ThreadLocal的为什么会内存泄露
在每一个线程Thread对象中都维护了一个ThreadLocalMap对象。ThreadLocalMap中又维护了一个k v 形式的Entry对象key指向了当前ThreadLocal对象value就是我们实际在ThreadLocal中存储的值。Entry中的key存放是ThreadLocal的弱引用。 因为ThreadLocalMap的key对它的引用是弱引用将会在下一次gc被回收那就会出现key变成null如果这时value外部也没有强引用指向它那么value就永远也访问不到了按理也应该被GC回收但是由于ThreadLocalMap.Entry对象还在强引用value导致value无法被回收这时「内存泄漏」就发生了value成了一个永远也无法被访问但是又无法被回收的对象。
为什么使用弱引用
假设key也用强引用指向当前ThreadLocal的话那么如果我这时候写 t1 null 按理说下次GC时应该要把堆内存的new ThreadLocal 这个对象进行回收才对但此时我的key如果设计成强引用显然GC无法对它进行回收因为key还强引用指向它。这就会造成内存泄漏所以ThreadLocal存值时key采用弱引用。key使用弱引用的特点就很明显了只要是GC回收不管内存够不够都会回收弱引用指向的对象当我写 t1 null 下次GC回收时就可以将new ThreadLocal 这个对象会被回收掉。
在 ThreadLocalMap 中的set/getEntry 方法中会对 key 为 null也即是 ThreadLocal 为 null 进行判断如果为 null 的话那么会把 value 置为 null 的这就意味着使用完 ThreadLocal , CurrentThread 依然运行的前提下就算忘记调用 remove 方法弱引用比强引用可以多一层保障弱引用的 ThreadLocal 会被回收对应value在下一次 ThreadLocaIMap 调用 set/get/remove 中的任一方法的时候会被清除从而避免内存泄漏
避免内存泄漏
将ThreadLocal设置为空之前执行remove方法会将key为空的键值对清空 尽量将ThreadLocal设置成static非必要尽量不要在ThreadLocal中放大对象