Java多线程异常抛出后的表现及捕获
一、多线程抛出异常后并不影响主线程及其他子线程的正常执行
public static void main(String[] args) {System.out.println("Main Thread start");Thread t1 = new Thread(new Runnable() {@Overridepublic void run() {int i = 0;while(i<7) {System.out.println("Thread1 i: "+(i++));try {Thread.sleep(1000);} catch (InterruptedException e) {e.printStackTrace();}if (i == 3) {throw new RuntimeException();}}}});Thread t2 = new Thread(new Runnable() {@Overridepublic void run() {int i = 0;while(i<7) {System.out.println("Thread2 i: "+(i++));try {Thread.sleep(1000);} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}}}});t2.start();t1.start();try {Thread.sleep(1000);} catch (InterruptedException e) {e.printStackTrace();}System.out.println("Main Thread end");}
运行结果
Main Thread start
Thread2 i: 0
Thread1 i: 0
Main Thread end
Thread1 i: 1
Thread2 i: 1
Thread1 i: 2
Thread2 i: 2
Exception in thread "Thread-0" java.lang.RuntimeExceptionat cc.eslink.safecheck.domain.dto.req.ProblemReq$1.run(ProblemReq.java:136)at java.lang.Thread.run(Thread.java:748)
Thread2 i: 3
Thread2 i: 4
Thread2 i: 5
Thread2 i: 6Process finished with exit code 0
二、多线程抛出异常主线程无法捕获
public static void main(String[] args) {System.out.println("Main Thread start");Thread t1 = new Thread(new Runnable() {@Overridepublic void run() {int i = 0;while(i<7) {System.out.println("Thread1 i: "+(i++));try {Thread.sleep(1000);} catch (InterruptedException e) {e.printStackTrace();}if (i == 3) {throw new RuntimeException();}}}});Thread t2 = new Thread(new Runnable() {@Overridepublic void run() {// TODO Auto-generated method stubint i = 0;while(i<7) {System.out.println("Thread2 i: "+(i++));try {Thread.sleep(1000);} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}}}});t2.start();try{t1.start();}catch (RuntimeException e){System.out.println("异常捕获");e.printStackTrace();}try {Thread.sleep(1000);} catch (InterruptedException e) {e.printStackTrace();}System.out.println("Main Thread end");}
运行结果
Main Thread start
Thread2 i: 0
Thread1 i: 0
Main Thread end
Thread2 i: 1
Thread1 i: 1
Thread1 i: 2
Thread2 i: 2
Thread2 i: 3
Exception in thread "Thread-0" java.lang.RuntimeExceptionat cc.eslink.safecheck.domain.dto.req.ProblemReq$1.run(ProblemReq.java:136)at java.lang.Thread.run(Thread.java:748)
Thread2 i: 4
Thread2 i: 5
Thread2 i: 6Process finished with exit code 0
三、捕获异常
Thread.UncaughtExceptionHandler是当线程因未捕获的异常而突然终止时调用的处理程序接口。
当一个线程由于未捕获的异常而即将终止时,Java虚拟机将使用它来 查询线程的 UncaughtExceptionHandler Thread.getUncaughtExceptionHandler(),并将调用该处理程序的 uncaughtException方法,并将该线程和异常作为参数传递。如果某个线程没有 显式设置其UncaughtExceptionHandler,则其ThreadGroup对象将充当其 UncaughtExceptionHandler。如果ThreadGroup对象没有处理异常的特殊要求,它可以将调用转发到默认的未捕获异常处理程序。
public static void main(String[] args) {System.out.println("Main Thread start");Thread t1 = new Thread(new Runnable() {@Overridepublic void run() {int i = 0;while(i<7) {System.out.println("Thread1 i: "+(i++));try {Thread.sleep(1000);} catch (InterruptedException e) {e.printStackTrace();}if (i == 3) {throw new RuntimeException();}}}});Thread t2 = new Thread(new Runnable() {@Overridepublic void run() {// TODO Auto-generated method stubint i = 0;while(i<7) {System.out.println("Thread2 i: "+(i++));try {Thread.sleep(1000);} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}}}});Thread.UncaughtExceptionHandler handler = new Thread.UncaughtExceptionHandler() {public void uncaughtException(Thread th, Throwable ex) {System.out.println("Uncaught exception: " + ex);}};t2.start();t1.setUncaughtExceptionHandler(handler);t1.start();try {Thread.sleep(1000);} catch (InterruptedException e) {e.printStackTrace();}System.out.println("Main Thread end");}
运行结果
Main Thread start
Thread2 i: 0
Thread1 i: 0
Main Thread end
Thread1 i: 1
Thread2 i: 1
Thread2 i: 2
Thread1 i: 2
Thread2 i: 3
Uncaught exception: java.lang.RuntimeException
Thread2 i: 4
Thread2 i: 5
Thread2 i: 6Process finished with exit code 0
四 线程池中异常捕获
1、execute方法,子线程中有异常会抛出异常;
public static void main(String[] args) {ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(2, 5, 1000, TimeUnit.SECONDS, new ArrayBlockingQueue<Runnable>(10));
for (int i=0;i<10;i++) {threadPoolExecutor.execute(()->doTask("execute"));}threadPoolExecutor.shutdown();}private static void doTask(String string)throws RuntimeException {String str = "ThreadName:"+ Thread.currentThread().getName()+"执行方式:"+string;System.out.println(str);List list = null;System.out.println(list.size()); }
2、submit方法,子线程中有异常不会抛出,需要使用future.get()方法获取异常信息;
public class ThreadPools {public static void main(String[] args) {ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(2, 5, 1000, TimeUnit.SECONDS, new ArrayBlockingQueue<Runnable>(10));for (int i=0;i<10;i++) {Future future = threadPoolExecutor.submit(()->doTask("submit"));try {future.get();} catch (InterruptedException e) {e.printStackTrace();} catch (ExecutionException e) {e.printStackTrace();}}threadPoolExecutor.shutdown();}private static void doTask(String string)throws RuntimeException {String str = "ThreadName:"+ Thread.currentThread().getName()+"执行方式:"+string;System.out.println(str);List list = null;System.out.println(list.size());/* try {System.out.println(list.size());}catch (Exception e) {System.out.println(e.getMessage());}
*/}
}
但是如果子线程中异常在子线程中被捕获到没有抛出,future.get()方法不会获取到异常信息;
public class ThreadPools {public static void main(String[] args) {ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(2, 5, 1000, TimeUnit.SECONDS, new ArrayBlockingQueue<Runnable>(10));for (int i=0;i<10;i++) {Future future = threadPoolExecutor.submit(()->doTask("submit"));try {future.get();} catch (InterruptedException e) {e.printStackTrace();} catch (ExecutionException e) {e.printStackTrace();}}threadPoolExecutor.shutdown();}private static void doTask(String string)throws RuntimeException {String str = "ThreadName:"+ Thread.currentThread().getName()+"执行方式:"+string;System.out.println(str);List list = null;try {System.out.println(list.size());}catch (Exception e) {System.out.println(e.getMessage());}}
Java多线程异常抛出后的表现及捕获相关推荐
- java中异常抛出后代码还会继续执行吗
java中异常抛出后代码还会继续执行吗 参考文章: (1)java中异常抛出后代码还会继续执行吗 (2)https://www.cnblogs.com/xiaoshen666/p/10848827.h ...
- Java 多线程异常捕获Runnable实现
1.背景: Java 多线程异常不向主线程抛,自己处理,外部捕获不了异常.所以要实现主线程对子线程异常的捕获. 2.工具: 实现Runnable接口的LayerInitTask类,ThreadExce ...
- java的异常抛出throws和throw的简单使用
java的异常抛出throws和throw的简单使用 参考文章: (1)java的异常抛出throws和throw的简单使用 (2)https://www.cnblogs.com/Anxc/p/113 ...
- java 多线程异常_java多线程执行异常
循环次数只有十次,执行的速度太快了,几乎可以忽略不计了,这正好说明了主线程直接先执行,然后Thread启动了run方法其次执行的道理,如果你想看到更真实的效果我建议你在线程中添加延迟,这样可以看的更加 ...
- java runnable 异常_Java实现多线程异常捕获Runnable的案例
这篇文章主要介绍了详解Java中多线程异常捕获Runnable的实现的相关资料,希望通过本文能帮助到大家,让大家理解掌握这样的知识,需要的朋友可以参考下 详解Java中多线程异常捕获Runnable的 ...
- java runnable 异常_详解Java中多线程异常捕获Runnable的实现
详解Java中多线程异常捕获Runnable的实现 1.背景: Java 多线程异常不向主线程抛,自己处理,外部捕获不了异常.所以要实现主线程对子线程异常的捕获. 2.工具: 实现Runnable接口 ...
- java 抛出异常的作用_Java 基础之异常抛出
Java 基础之异常抛出 Java,基础,异常抛出 在 Java 里,除了对异常的捕获外,你还可以抛出异常,还可以创造异常.抛出异常的作用就是告诉你的调用者,程序出现了不正常的情况了,得不要期望的结果 ...
- java 之 异常
/* 异常总结: 异常是什么: 是对问题的描述,将问题进行对象的封装. 异常体系: Throwable |--Error |--Exception |--RuntimeExceptio ...
- Java笔记(异常)
文章目录 异常 概念 必要性 分类 Throwable(可抛出的) Error(错误) Exception 常见异常 异常的产生 自动抛出异常 手动抛出异常(throw) 异常处理 try...cat ...
最新文章
- Oracle 11g新特性之--只读表(read only table)
- 笔记-信息化与系统集成技术-信息的质量属性
- 连号区间数(2013年第四届c/c++ b组第10题)
- springboot转发http请求_网易后端实习生分享:Springboot异常和错误处理规范
- C#开发笔记之14-如何用C#计算闰年?
- 在react开发过程中由于setState的异步特性,获取最新state遇到问题
- Day 6 函数与模块
- 【正点原子FPGA连载】第三十二章 MDIO接口读写测试实验-摘自【正点原子】领航者ZYNQ之FPGA开发指南_V2.0
- 第三方支付牌照(支付业务许可证)
- SpringBoot、SpringCloud版本中GA/PRE/SNAPSHOT的详解
- 模拟器和平精英连接服务器没有响应,和平精英模拟器卡顿解决方法一览
- 港科夜闻|香港科技大学校长叶玉如教授,新加坡国立大学曾运雄博士:发现阿尔茨海默病新疗法...
- unity3d-unet小demo
- 各种艺术字、图片在线制作
- 鲲鹏服务器gpu型号,GPU服务器服务
- 重装系统后通过修改注册表实现记录还原
- WordPress丨关于国内的个人头像无法获取问题以及解决方案
- 九校联考-长沙市一中NOIP模拟Day2T1 旋转子段(rotate)
- 高等数学复习之导数的运算(等价无穷小替换)
- 2019 年值得学习的顶级 JavaScript 框架与主题