一、ThreadLocal内存泄露案例
/*** @Author : 一叶浮萍归大海* @Date: 2023/11/22 10:56* @Description: 写一段代码导致内存泄露* VM Options:-Xms20m -Xmx20m -Xmn10m -XX:+PrintGCDetails* 说明:内存泄露最终会导致内存溢出*/
public class ThreadLocalOomMainApp {public static void main(String[] args) {// 可重入锁Lock lock = new ReentrantLock();// 是否调用remove()方法boolean remove = false;// 线程池ExecutorService pool = new ThreadPoolExecutor(2,10,2L,TimeUnit.SECONDS,new ArrayBlockingQueue<>(20),Executors.defaultThreadFactory(),// new ThreadPoolExecutor.AbortPolicy// new ThreadPoolExecutor.CallerRunsPolicy// new ThreadPoolExecutor.DiscardOldestPolicynew ThreadPoolExecutor.DiscardOldestPolicy());for (int i = 1; i <= 20; i++) {pool.execute(() -> {try {lock.lock();// 为了不重复使用线程,使用map标记已经使用过的线程Map<Long, Integer> map = new ConcurrentHashMap<>(10);Integer num = map.putIfAbsent(Thread.currentThread().getId(), 1);if (num == null) {ThreadLocal<Byte[]> threadLocal = new ThreadLocal<>();threadLocal.set(new Byte[1024 * 1024]);if (remove) {// 解决内存泄露的关键threadLocal.remove();}// 将threadLocal置位空,利于GC回收threadLocal = null;// 手工触发GCSystem.gc();// 调用GC后不一定马上回收,模拟等待GC回收的时间Thread.sleep(50);}} catch (Exception e) {e.printStackTrace();} finally {lock.unlock();}});}System.out.println(Thread.currentThread().getName());}}