第09章:随堂复习与企业真题(异常处理)

一、随堂复习

1. 异常的概述

1. 什么是异常?
指的是程序在执行过程中,出现的非正常情况,如果不处理最终会导致JVM的非正常停止。
​
2. 异常的抛出机制
Java中把不同的异常用不同的类表示,一旦发生某种异常,就`创建该异常类型的对象`,并且抛出(throw)。
然后程序员可以捕获(catch)到这个异常对象,并处理;如果没有捕获(catch)这个异常对象,那么这个异常
对象将会导致程序终止。
​
3. 如何对待异常
 对于程序出现的异常,一般有两种解决方法:一是遇到错误就终止程序的运行。另一种方法是程序员在编写程序时,
 就充分考虑到各种可能发生的异常和错误,极力预防和避免。实在无法避免的,要编写相应的代码进行异常的检测、
 以及`异常的处理`,保证代码的`健壮性`。

2. 异常的体系结构及常见的异常

java.lang.Throwable:异常体系的根父类
    |---java.lang.Error:错误。Java虚拟机无法解决的严重问题。如:JVM系统内部错误、资源耗尽等严重情况。
                         一般不编写针对性的代码进行处理。
               |---- StackOverflowError、OutOfMemoryError
​
    |---java.lang.Exception:异常。我们可以编写针对性的代码进行处理。
               |----编译时异常:(受检异常)在执行javac.exe命令时,出现的异常。
                    |----- ClassNotFoundException
                    |----- FileNotFoundException
                    |----- IOException
               |----运行时异常:(非受检异常)在执行java.exe命令时,出现的异常。
                    |---- ArrayIndexOutOfBoundsException
                    |---- NullPointerException
                    |---- ClassCastException
                    |---- NumberFormatException
                    |---- InputMismatchException
                    |---- ArithmeticException
【面试题】说说你在开发中常见的异常都有哪些?
​
开发1-2年:
|----编译时异常:(受检异常)在执行javac.exe命令时,出现的异常。
    |----- ClassNotFoundException
    |----- FileNotFoundException
    |----- IOException
|----运行时异常:(非受检异常)在执行java.exe命令时,出现的异常。
    |---- ArrayIndexOutOfBoundsException
    |---- NullPointerException
    |---- ClassCastException
    |---- NumberFormatException
    |---- InputMismatchException
    |---- ArithmeticException
​
开发3年以上:
OOM。

3. 异常处理的方式

过程1:“抛”
 >"自动抛" : 程序在执行的过程当中,一旦出现异常,就会在出现异常的代码处,自动生成对应异常类的对象,并将此对象抛出。
​
 >"手动抛" :程序在执行的过程当中,不满足指定条件的情况下,我们主动的使用"throw + 异常类的对象"方式抛出异常对象。
​
​
过程2:“抓”
    狭义上讲:try-catch的方式捕获异常,并处理。
    广义上讲:把“抓”理解为“处理”。则此时对应着异常处理的两种方式:① try-catch-finally ② throws
3.1 try-catch-finally
1. 基本结构:
try{
   ...... //可能产生异常的代码
}
catch( 异常类型1 e ){
   ...... //当产生异常类型1型异常时的处置措施
}
catch( 异常类型2 e ){
   ......     //当产生异常类型2型异常时的处置措施
}
finally{
   ...... //无论是否发生异常,都无条件执行的语句
}
​
2. 使用细节:
> 将可能出现异常的代码声明在try语句中。一旦代码出现异常,就会自动生成一个对应异常类的对象。并将此对象抛出。
> 针对于try中抛出的异常类的对象,使用之后的catch语句进行匹配。一旦匹配上,就进入catch语句块进行处理。
  一旦处理接触,代码就可继续向下执行。
> 如果声明了多个catch结构,不同的异常类型在不存在子父类关系的情况下,谁声明在上面,谁声明在下面都可以。
  如果多个异常类型满足子父类的关系,则必须将子类声明在父类结构的上面。否则,报错。
> catch中异常处理的方式:
   ① 自己编写输出的语句。
   ② printStackTrace():打印异常的详细信息。 (推荐)
   ③ getMessage():获取发生异常的原因。
> try中声明的变量,出了try结构之后,就不可以进行调用了。
> try-catch结构是可以嵌套使用的。
3. finally的使用说明:
3.1 finally的理解
> 我们将一定要被执行的代码声明在finally结构中。
> 更深刻的理解:无论try中或catch中是否存在仍未被处理的异常,无论try中或catch中是否存在return语句等,finally
  中声明的语句都一定要被执行。
​
> finally语句和catch语句是可选的,但finally不能单独使用。
​
3.2 什么样的代码我们一定要声明在finally中呢?
> 我们在开发中,有一些资源(比如:输入流、输出流,数据库连接、Socket连接等资源),在使用完以后,必须显式的进行
关闭操作,否则,GC不会自动的回收这些资源。进而导致内存的泄漏。
  为了保证这些资源在使用完以后,不管是否出现了未被处理的异常的情况下,这些资源能被关闭。我们必须将这些操作声明
在finally中!
3.2 throws
1. 格式:在方法的声明除,使用"throws 异常类型1,异常类型2,..."
​
2. 举例:
​
public void test() throws 异常类型1,异常类型2,.. {
    //可能存在编译时异常
}
​
​
3. 是否真正处理了异常?
> 从编译是否能通过的角度看,看成是给出了异常万一要是出现时候的解决方案。此方案就是,继续向上抛出(throws)。
> 但是,此throws的方式,仅是将可能出现的异常抛给了此方法的调用者。此调用者仍然需要考虑如何处理相关异常。
  从这个角度来看,throws的方式不算是真正意义上处理了异常。
​
​
4. 方法的重写的要求:(针对于编译时异常来说的)
子类重写的方法抛出的异常类型可以与父类被重写的方法抛出的异常类型相同,或是父类被重写的方法抛出的异常类型的子类。

开发中的经验之谈:

开发中,如何选择异常处理的两种方式?(重要、经验之谈)
- 如果程序代码中,涉及到资源的调用(流、数据库连接、网络连接等),则必须考虑使用try-catch-finally来处理,
  保证不出现内存泄漏。
- 如果父类被重写的方法没有throws异常类型,则子类重写的方法中如果出现异常,只能考虑使用try-catch-finally
  进行处理,不能throws。
- 开发中,方法a中依次调用了方法b,c,d等方法,方法b,c,d之间是递进关系。此时,如果方法b,c,d中有异常,
  我们通常选择使用throws,而方法a中通常选择使用try-catch-finally。

4. 手动throw异常对象

在方法内部,满足指定条件的情况下,使用"throw 异常类的对象"的方式抛出。

5. 如何自定义异常类

① 继承于现有的异常体系。通常继承于RuntimeException \ Exception
② 通常提供几个重载的构造器
③ 提供一个全局常量,声明为:static final long serialVersionUID;
为什么需要自定义异常类?
我们其实更关心的是,通过异常的名称就能直接判断此异常出现的原因。既然如此,我们就有必要在实际开发场景中,
不满足我们指定的条件时,指明我们自己特有的异常类。通过此异常类的名称,就能判断出具体出现的问题。

二、企业真题

2.1 异常概述

1. Java的异常体系简单介绍下(网*)
包含问题:
> 4.异常的顶级接口是什么(软**力)
> 异常类的继承关系,exception下都有哪些类?(上海*冉信息)
java.lang.Throwable:异常体系的根父类
    |---java.lang.Error:错误。Java虚拟机无法解决的严重问题。如:JVM系统内部错误、资源耗尽等严重情况。
                         一般不编写针对性的代码进行处理。
               |---- StackOverflowError、OutOfMemoryError
​
    |---java.lang.Exception:异常。我们可以编写针对性的代码进行处理。
               |----编译时异常:(受检异常)在执行javac.exe命令时,出现的异常。
                    |----- ClassNotFoundException
                    |----- FileNotFoundException
                    |----- IOException
               |----运行时异常:(非受检异常)在执行java.exe命令时,出现的异常。
                    |---- ArrayIndexOutOfBoundsException
                    |---- NullPointerException
                    |---- ClassCastException
                    |---- NumberFormatException
                    |---- InputMismatchException
                    |---- ArithmeticException
2. Java异常处理机制(*科软)

两种处理方案:try-catch-finally ;throws

3. 异常的两种类型,Error和Exception的区别(上海冠*新创、北京中**译、*度)
|---java.lang.Error:错误。Java虚拟机无法解决的严重问题。如:JVM系统内部错误、资源耗尽等严重情况。
                         一般不编写针对性的代码进行处理。
               |---- StackOverflowError、OutOfMemoryError
​
|---java.lang.Exception:异常。我们可以编写针对性的代码进行处理。
               |----编译时异常:(受检异常)在执行javac.exe命令时,出现的异常。
                    |----- ClassNotFoundException
                    |----- FileNotFoundException
                    |----- IOException
               |----运行时异常:(非受检异常)在执行java.exe命令时,出现的异常。
                    |---- ArrayIndexOutOfBoundsException
                    |---- NullPointerException
                    |---- ClassCastException
                    |---- NumberFormatException
                    |---- InputMismatchException
                    |---- ArithmeticException
4. 运行时异常与一般异常有何异同?(华*思为)

运行时异常:RuntimeException

  • 编译可以通过。在运行时可能抛出。出现的概率高一些;一般针对于运行时异常,都不处理。

一般异常:Exception

  • 编译不能通过。要求必须在编译之前,考虑异常的处理。不处理编译不通过。

5. 说几个你常见到的异常(华油**普)
类似问题:
> 请列出Java中常见的几种异常?(百*园)
> 给我一个你最常见到的runtime exception。(*蝶)
开发1-2年:
|----编译时异常:(受检异常)在执行javac.exe命令时,出现的异常。
    |----- ClassNotFoundException
    |----- FileNotFoundException
    |----- IOException
|----运行时异常:(非受检异常)在执行java.exe命令时,出现的异常。
    |---- ArrayIndexOutOfBoundsException
    |---- NullPointerException
    |---- ClassCastException
    |---- NumberFormatException
    |---- InputMismatchException
    |---- ArithmeticException
​
开发3年以上:
OOM。

2.2 try-catch-finally

1. 说说final、finally、finalize的区别(北京中**译、艾*软件、拓*思、*科软)
类似问题:
> 1. finally和final的区别(*科软)

引用finalize的回答:链接

1.    finally的理解
    > 我们将一定要被执行的代码声明在finally结构中。
    > 更深刻的理解:无论try中或catch中是否存在仍未被处理的异常,无论try中或catch中是否存在        
      return语句等,finally中声明的语句都一定要被执行。
​
    > finally语句和catch语句是可选的,但finally不能单独使用。

2.    final关键字的使用

2.1   final的理解:最终的

2.2   final可以用来修饰的结构:类、方法、变量

2.3.  具体说明:

2.3.1 final修饰类:表示此类不能被继承。
      比如:String、StringBuffer、StringBuilder类

2.3.2 final修饰方法:表示此方法不能被重写
      比如:Object类中的getClass()

2.3.3 final修饰变量:既可以修饰成员变量,也可以修饰局部变量。
      此时的"变量"其实就变成了"常量",意味着一旦赋值,就不可更改。

      1 final修饰成员变量: 有哪些位置可以给成员变量赋值?
        > 显式赋值
        > 代码块中赋值
        > 构造器中赋值

      2 final修饰局部变量:一旦赋值就不能修改
        > 方法内声明的局部变量:在调用局部变量前,一定需要赋值。而且一旦赋值,就不可更改
        > 方法的形参:在调用此方法时,给形参进行赋值。而且一旦赋值,就不可更改

2.4   final与static搭配:修饰成员变量时,此成员变量称为:全局常量。
      比如:Math的PI

3. finalize
    当JVM调用GC时就会调用此方法,但清除此方法的对象要至少调用两次GC。
    在Java中,finalize()方法是Object类的一个方法,用于在垃圾回收器确定没有活跃的引用指向对象时被调用。
    finalize()方法的调用时机并不是确定的,因为垃圾回收器的执行是由Java虚拟机控制的。通常情况下,当垃圾回收器准备回收一个对象的内存时,会调用该对象的finalize()方法来执行—些清理操作。
2. 如果不使用try-catch,程序出现异常会如何?(上海冠*新创科技)

对于当前方法来讲,如果不使用try-catch,则在出现异常对象以后会抛出此对象。如果没有处理方案,就会终止程序的执行。

3. try ... catch捕捉的是什么异常?(北京亿*东方)

Exception。非Error

4. 如果执行finally代码块之前方法返回了结果或者jvm退出了,这时finally块中的代码还会执行吗?(恒*电子)

特别的:System.exit(0);不会执行

5. 在try语句中有return语句,最后写finally语句,finally语句中的code会不会执行?何时执行?如果执行是在return前还是后(拓*思、华**为)

会,return后,再finally,再return的返回

6. 捕获异常在catch块里一定会进入finally吗?catch里能return吗?catch里return还会进finally吗?在try里return是什么情况?(*蓝)

会;会;会;会,return后,再finally,再return的返回

2.3 throw与throws

1. throw和throws的区别?(北京亿**方、北京新*阳光)
从使用上讲:throws用在方法声明处,把产生的异常对象继续向上抛出,属于异常处理方式。处理异常
          throw使用在方法内部,后面跟着异常类的对象,表示手动抛出异常类的对象。产生异常
          用的场景不一样

角度1:"形",即使用的格式

throw:使用在方法内部,“throw 异常类的对象”
throws:使用在方法的声明处,"throws 异常类1,异常类2,..."

角度2:"角色"或作用不同。

上游排污,下游治污。
​
过程1:“抛”
    >throw
过程2:“抓”
    > try-catch ; throws

2. 子类重写父类抛出异常的方法,能否抛出比父类更高级别的异常类(顺*)

不能!只能和父类一样,或者为父类的子类。

2.4 自定义异常

1. 如何自定义一个异常?(*软国际)
1. 如何自定义异常类?
① 继承于现有的异常体系。通常继承于RuntimeException \ Exception
② 通常提供几个重载的构造器
③ 提供一个全局常量,声明为:static final long serialVersionUID;

2. 如何使用自定义异常类?

> 在具体的代码中,满足指定条件的情况下,需要手动的使用"throw + 自定义异常类的对象"方式,将异常对象抛出。
> 如果自定义异常类是非运行时异常,则必须考虑如何处理此异常类的对象。(具体的:① try-catch-finally ② throws)

3. 为什么需要自定义异常类?
我们其实更关心的是,通过异常的名称就能直接判断此异常出现的原因。既然如此,我们就有必要在实际开发场景中,
不满足我们指定的条件时,指明我们自己特有的异常类。通过此异常类的名称,就能判断出具体出现的问题。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值