java----异常处理

解决异常的方案:

1.把不同类型的异常情况描述成不同类
2.分离异常流程代码和正确流程代码
3.灵活处理异常,如果当前处理不了,则应交给调用者来处理
-----------------------------------------------------------------------------------------------------------------------------------------------------------

种类:

1.Error: 表示错误,一般指JVM相关的不可修复的错误,如系统崩溃,内存溢出,JVM出错。由JVM处理,不需要我们处理
2.Exception:表示异常,指程序中出现不正常的情况,该问题可以修复(异常出现后,程序会中断,所以必须处理异常)
-------------------------------------------------------------------------------------------------------------------------------------------------------------

如果异常出现的话,就会立刻终止程序,我们要处理异常:

1.该方法不处理,而是声明抛出,该方法的调用者会来处理
2.在方法内使用try-catch的语句块来处理异常
---------------------------------------------------------------------------------------------------------------------------------------------------------------------

使用try-catch捕获单个异常,语法如下:

try{
编写可能会出现异常的代码 // 出现异常后程序会中断执行,所以要处理异常
}catch(Exception e){
处理异常的代码
}

注意:try和catch都不能单独使用

sop("begin..........");
try{
int res = 10/0 ; // 出现异常后程序会中断执行,所以要处理异常
sop("result:"+res); // 因为 res哪行出现了异常,所以就不会执行这行代码了
}catch(ArithmeticException e){ // 如果是别的异常那么就不会处理,只能捕获算数异常
sop("bad!");
}


sop("end............");


-----------------------------------------------------------------------------------------------------------------------------------------------------------------------

获取异常信息:

1.String getMessage():获取异常信息的描述,原因(提示给用户的时候就提示这个原因)
2.String toString() : 获取异常类型和异常描述信息(一般不用)
3.void printStackTrace():打印异常的跟踪栈信息,不需要使用System.out.print。 包括了异常的类型,异常的原因,还包括异常出现的位置,在开发和调试阶段,都需要使用该方法
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

获取try-catch捕获多个异常

String sNum1 = "10";
String sNum2 = "2s";
try {


int Num1 = Integer.parseInt(sNum1);
// 转换出错了,所以之前的都执行了,直接跳转到 NumberFormatException
int Num2 = Integer.parseInt(sNum2);
int res = Num1 / Num2 ;
sop("result:"+res);

} catch (ArithmeticException e) {
// TODO: handle exception
sop("除数为0");
}catch(NumberFormatException e){
sop("转换出错");
}catch(Exception e){
// 都不属于算数异常的时候,才执行这句话。先找专业的,专业的没有再找公共的
//这个大的boss要放在后面,如果放到前面,他就直接接受了所有的了
e.printStackTrace();
}

----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

finally语句块表示最终都会执行的代码,无论有没有异常:


-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

什么时候的代码块必须执行:

当我们 try语句块中打开了一些物理资源(磁盘文件/网络连接/数据库连接等),我们都得在使用完后,最终关闭资源
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

finally的两种语法:

1.try........finally:此时没有使用catch来捕获异常,因为此时根据应用场景,我们会抛出异常,自己不处理

try {
int res = 10/0 ;
} finally{
sop("关闭资源");
}


2.try......catch.........finally:自身需要处理异常,最终还得关闭资源。

try {
int res = 10/0 ;
} catch (ArithmeticException e) {
sop("除数为0");
}finally{
sop("关闭资源");
}

注意:finally不能单独使用
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

Finally没有执行的情况

1.当只有在try或者catch中调用了退出JVM的相关方法,此时finally才不会执行,否则它永远都会执行。(System..exit(0);)

----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

Finally的要求

1.只有finally中的代码才会一定返回,其他的不一定执行
2.如果finally中有return语句,永远返回finally的结果,避免该情况的出现
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

Finally的执行顺序

结论:
1、不管有木有出现异常,finally块中代码都会执行;
2、当try和catch中有return时,finally仍然会执行;
3、finally是在return后面的表达式运算后执行的(此时并没有返回运算后的值,而是先把要返回的值保存起来,管finally中的代码怎么样,返回的值都不会改变,任然是之前保存的值),所以函数返回值是在finally执行前确定的;
4、finally中最好不要包含return,否则程序会提前退出,返回值不是try或catch中保存的返回值。
举例:
情况1 :try{} catch(){}finally{} return;
            显然程序按顺序执行。
情况2 :try{ return; }catch(){} finally{} return;
          程序执行try块中return之前(包括return语句中的表达式运算)代码;
         再执行finally块,最后执行try中return;
         finally块之后的语句return,因为程序在try中已经return所以不再执行。
情况3 :try{ } catch(){return;} finally{} return;
         程序先执行try,如果遇到异常执行catch块,
         有异常:则执行catch中return之前(包括return语句中的表达式运算)代码,再执行finally语句中全部代码,
                     最后执行catch块中return. finally之后也就是4处的代码不再执行。
         无异常:执行完try再finally再return.
情况4 :try{ return; }catch(){} finally{return;}
          程序执行try块中return之前(包括return语句中的表达式运算)代码;
          再执行finally块,因为finally块中有return所以提前退出。
情况5 :try{} catch(){return;}finally{return;}
          程序执行catch块中return之前(包括return语句中的表达式运算)代码;
          再执行finally块,因为finally块中有return所以提前退出。
情况6 :try{ return;}catch(){return;} finally{return;}
          程序执行try块中return之前(包括return语句中的表达式运算)代码;
          有异常:执行catch块中return之前(包括return语句中的表达式运算)代码;
                       则再执行finally块,因为finally块中有return所以提前退出。
          无异常:则再执行finally块,因为finally块中有return所以提前退出。

最终结论 :任何执行try 或者catch中的return语句之前,都会先执行finally语句,如果finally存在的话。
                  如果finally中有return语句,那么程序就return了,所以finally中的return是一定会被return的,
                  编译器把finally中的return实现为一个warning。
-------------------------------------------------------------------------------------------------------------------

异常的分类:

1.编译时期异常:checked异常,在编译时期就会检查,如果没有处理异常,则会编译失败
2.运行时期异常:runtime异常,在运行时期,检查异常,在编译时期运行异常不会编译器检测,运行异常编译时期,可以处理可以不处理

---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

Throw语句:

运用于方法内部,抛出一个具体的异常对象。
throw new 异常类(“异常信息”);终止方法
throw : 一般的,当一个方法出现不正常的情况的时候,我们不知道该方法应该返回什么此时就返回一个错误,在catch语句中继续向上抛出
return是返回一个值,throw是返回一个错误,返回给该方法的调用者
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

自定义异常类

我们说java中不同的异常类,分别代表着某一种具体的异常情况,SUN公司没有定义好的,我们需要根据自己的业务逻辑来编写异常

------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

异常类如何定义:

1.定义一个受检查的异常类
2.自定义一个运行时期的异常类

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

异常转译:

当位于最上层的子系统不需要关心底层的异常细节时,常见的做法是捕获原始的异常,把它作为一个新的不同类型的异常,在抛出新的异常,我在catch中重新抛出一个新的异常。因为很多情况下下层不关心上层信息。
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

异常链:

把原始的异常包装为新的异常类,从而形成多个异常的有序排列,有助于查找出异常的根本原因

-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

处理异常的原则:

1.异常只能用于非正常情况,try-catch的存在也会影响性能
2.需要为异常提供说明文档,如果自定义了一个异常或者某一个方法抛出了异常,我们应该记录文档注释
3.尽可能避免异常
4.异常的粒度很重要,应该为一个基本操作定义一个try-catch块,不要为了简便将几百行代码同时放入一个try-catch中
5.建议在循环中进行异常处理,应该在循环外对异常进行捕获处理
6.自定义异常尽量使用RuntimeException类型



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值