美文网首页
Java线程池异常处理

Java线程池异常处理

作者: 明翼 | 来源:发表于2018-05-09 18:41 被阅读12次

起因

在Java默认的线程池中执行的程序,如果程序产生异常导致线程池里面的线程死掉,完全没有任何信息抛出来,这个是个很可怕的事情,程序静默,从日志看不到任何有用信息。

解决办法

线程池一般有两种提交办法:通过execute和submit两种方式往线程池提交我们的任务。

  1. 如果是execute 这种可以通过继承线程池,然后处理:
  
import java.util.concurrent.BlockingQueue;  
import java.util.concurrent.ThreadPoolExecutor;  
import java.util.concurrent.TimeUnit;  
  
public class MyThreadPoolExecutor extends ThreadPoolExecutor {  
  
    public MyThreadPoolExecutor(int corePoolSize, int maximumPoolSize,  
            long keepAliveTime, TimeUnit unit, BlockingQueue<Runnable> workQueue) {  
        super(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue);  
    }  
  
    @Override  
    protected void afterExecute(Runnable r, Throwable t) {  
        super.afterExecute(r, t);  
        System.out.println("MyThreadPoolExecutor.afterExecute()");  
        if (t != null) {
            System.out.println("Error msg:{}",t.getMessage());  
        }
    }  
  
}  

2)如果是submit方式提交:

protected void afterExecute(Runnable r, Throwable t) {  
    super.afterExecute(r, t);  
    Future<?> f = (Future<?>) r;  
    try {  
        f.get();  
    } catch (InterruptedException e) {  
        logger.error("线程池中发现异常,被中断", e);  
    } catch (ExecutionException e) {  
        logger.error("线程池中发现异常,被中断", e);  
    }  
  
}  

总结

最终采用如下的代码,可能不高效,但是异常都可以捕获到。

package threads;

import java.util.concurrent.BlockingQueue;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Future;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class MyThreadExcutor extends ThreadPoolExecutor {

    private static final Logger logger = LoggerFactory.getLogger(MyThreadExcutor.class);

    public MyThreadExcutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit,
            BlockingQueue<Runnable> workQueue) {
        super(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue);

    }

    @Override
    protected void afterExecute(Runnable r, Throwable t) {
        super.afterExecute(r, t);
        if (t != null) {
            logger.error("Find exception error reason :{}", t.getMessage());
        }

        Future<?> f = (Future<?>) r;
        try {
            f.get();
        } catch (InterruptedException e) {
            logger.error("线程池中发现异常,被中断", e);
        } catch (ExecutionException e) {
            logger.error("线程池中发现异常,被中断", e);
        }

    }
}

相关文章

  • Java线程池异常处理

    起因 在Java默认的线程池中执行的程序,如果程序产生异常导致线程池里面的线程死掉,完全没有任何信息抛出来,这个是...

  • Java线程池异常处理方案

    执行多线程并发任务的时候,如果任务类型相同,一般会考虑使用线程池,一方面利用了并发的优势,一方面避免创建大量线程得...

  • python3 线程池和异常处理

    引用 线程池的基本使用as_completedwaitmap 线程池的异常处理 进程池用法 引用 Python中已...

  • 线程池异常处理

    一个栗子 模拟线程池中任务在执行过程中发生异常。 这段代码在执行中,肯定会报一个除0异常,但是我们不会收到任何错误...

  • Java多线程异常处理

    线程异常处理 Java中每个线程的异常处理是相互独立的,一个线程产生的异常不会影响其他线程的正常运行。因此,也不能...

  • Java线程池异常处理正确姿势

    假设我们有一个线程池,由于程序需要,我们向该线程池中提交了好多好多任务,但是 这些任务都没有对异常进行try ca...

  • Java面试题——多线程

    Java面试题——多线程 1,什么是线程池? 线程池是多线程的一种处理方式,处理过程中将任务提交给线程池,任务执行...

  • 【JAVA提升】- 线程、线程池、并发包(3)

    1.线程池(java.util.concurrent) 为什么要有线程池 ? 我们知道。使用线程来处理任务,可以达...

  • Java高并发系列——检视阅读(三)

    JAVA线程池 线程池实现原理 类似于一个工厂的运作。 当向线程池提交一个任务之后,线程池的处理流程如下: 判断是...

  • 线程池设计

    使用线程池的场合 单个任务处理时间短 将需处理的任务数量大 使用Java线程池好处 1、使用new Thread(...

网友评论

      本文标题:Java线程池异常处理

      本文链接:https://www.haomeiwen.com/subject/atdorftx.html