西故山 > 旅游 > 途中趣谈 > 趣谈Java中的异常处理

趣谈Java中的异常处理

来源:网络转载 2015-01-23 23:29 编辑: www.xigushan.com 查看:

标签:java   异常处理   趣味解析   

概述

顾名思义,通俗来讲异常就是指,那些发生在我们原本考虑和设定的计划之外的意外情况。

生活中总是会存在各种突发情况,如果没有做好准备,就让人措手不及。

你和朋友约好了明天一起去登山,半道上忽然乌云蔽日,下起了磅礴大雨。这就是所谓的异常情况。

你一下子傻眼了,然后看见朋友淡定的从背包里掏出一件雨衣穿上,淫笑着看着你。这就是对异常的处理。


对于一个OO程序猿来讲,所做的工作就是:将需要处理的现实生活中的复杂问题,抽象出来编写成为程序。

既然现实生活中总是存在着各种突然的异常情况,那么对应其抽象出的代码,自然也是存在这样的风险的。

所以常常说:要编写一个完善的程序并不只是简简单单的把功能实现,还要让程序具备处理在运行中可能出现的各种意外情况的能力。

这就是所谓的异常的使用。


体系


技术分享

这就是Java当中异常体系的结构构成,从图中我们可以提取到的信息就是:

1、Java中定义的所有异常类都是内置类Throwable的子类。


2、Java中的异常通常被分为两大类:Error和Exception:

  • 那么顾名思义,Error代表错误,Exception代表异常;
  • Error用以指明与运行环境相关的错误,JVM无法从此类错误中恢复,此类异常无需我们处理;
  • Exception代表着可以被我们所处理的异常情况,我们需要掌握和使用的,正是该类型。
  • 3、Exception最常见的两种异常类型分别是:

  • IOException:主要是用以处理操作数据流时可能会出现的各种异常情况。
  • RuntimeException:指发生在程序运行时期的异常,如数组越界,入参不满足规范等情况引起的程序异常

  • 工欲善其事,必先利其器

    要理解Java中的异常使用,首先要明白几个关于异常处理的工具 - 异常处理关键字的使用。

    1、throw:用以在方法内部抛出指定类型的异常。

    void test(){ if(发生异常的条件){ thorw new Exception("抛出异常"); } }

    2、throws:用以声明 一个方法可能发生的异常(通常都是编译时检测异常)有哪些。

    void test() throws 异常1,异常2{ //这个方法可能发生异常1,异常2 throw new 异常1(); throw new 异常2();  }3、try - catch:另一种处理异常的方式,与throws不同的是,这种方式是指 "捕获并处理"的方式。

    用try语句块包含可能发生异常的代码,catch用于捕获发生的异常,并在catch语句块中定义对捕获到的异常的处理方式。

    try { //可能发生异常的代码 } catch (要捕获的异常类型 e) { //对捕获到的异常的处理方式 }4、finally语句块:通常都是跟在try或try-catch之后进行使用,与其名字代表的一样。也就是定义最终的操作。

    特点是被try语句块包含的内容中,是否真的发生了异常。程序最终都将执行finally语句块当中的内容。

    通常用于对资源的释放操作,例如:通过JDBC连接数据库等情况。

    try { //获取资源 } catch (要捕获的异常类型 e) { //对捕获到的异常的处理方式 }finally{ //释放资源 }
    趣解异常的实际使用


    了解Java中异常类的实际应用之前,应当先了解两个概念,用以对最常用的异常做一个分类:


    1、编译时被检测异常:

       只要是Exception和其子类都是,除了特殊子类RuntimeException体系。

       所谓的编译时被检测异常也就是指在程序的编译器就会进行检测的异常分类。


       也就是说,如果一个方法抛出了一个编译时检测异常,Java则要求我们必须进行处理。

       既:通过throws对异常进行声明处理 或是 通过try-catch对异常进行捕获处理。

       如果程序编译时检测到该类异常没有被进行任何处理,那么编译器则会报出一个编译错误。

    public class Test{ public static void main(String[] args) { try { Class clazz = Class.forName("Java"); System.out.println(clazz.getName()); } catch (ClassNotFoundException e) { System.out.println("没有找到该类"); } } }

    上面代码中的ClassNotFoundException就是一种编译时检测异常,这个异常是由Class类当中的forName方法所抛出并声明的。

    如果我们在使用该方法时没有对异常进行处理:声明或捕获,那么该程序就会编译失败。


    通过这个例子想要说明的是:编译时被检测异常通常都是指那些“可以被我们预见”的异常情况。

    正例如:我们通过Class.forName是想要获取指定类的字节码文件对象,所以我们自然也可以预见可能会存在:

    与我们传入的类名参数所对应的类字节码文件对象不存在,查找不到的情况。

    既然这种意外情况是可以被预见的,那自然就应该针对其制定一些应对方案。


    2、编译时不检测异常(运行时异常):

       就是指Exception下的子类RuntimeException和其子类。

       通常这种问题的发生,会导致程序功能无法继续、运算无法进行等情况发生;

      

       但这类异常更多是因为调用者的原因或者引发了内部状态的改变而导致的。

       所以针对于这种异常,编译器不要求我们处理,可以直接编译通过。

       而在运行时,让调用者调用时的程序强制停止,从而让调用者对自身的代码进行修正。


    曾经看到过一道面试题:列出你实际开发中最常见的五个运行时异常,就我自己而言,如果硬要说出五个,那可能是:

    NullPointerException(空指针异常)、IndexOutOfBoundsException(角标越界异常)、ArithmeticException(异常运算条件异常)