zoukankan      html  css  js  c++  java
  • Java 异常基础详解

    1. Java 中的异常

    前言:Java 中的异常处理是处理程序运行错误时的强大机制之一,它可以保证应用程序的正常流程。

    首先我们将了解java异常、异常的类型以及受查和非受查异常之间的区别。

    1.1 什么是异常?

    字面意义:异常是一种不正常的情况。

    在 java 中,异常是扰乱程序正常流程的事件,它是在程序运行时抛出的对象。

    1.2 什么是异常处理?

    异常处理一种在运行时解决程序错误的机制,例如 ClassNotFound、IO、SQL、Remote 等。

    1.2.1 异常处理的优势

    异常通常会干扰程序的正常流程,而异常处理的核心优势是维护程序的正常流程。现在让我们假设一下:

    statement 1;  
    statement 2;  
    statement 3;  
    statement 4;  
    statement 5;//发生异常
    statement 6;  
    statement 7;  
    statement 8;  
    statement 9;  
    statement 10;  

    假设你的程序中有10条语句,如果在第5条中出现了一个异常,那么语句6-10将不会继续执行。如果你使用了异常处理,那么语句6-10的部分将正常执行,这就是我们为什么需要在程序中使用异常处理的原因。

    1.3 Java 异常类的层次结构

    throwable

    1.4 异常类型

    主要有两种类型的异常:受查和非受查异常,Error被视为非受查异常。Sun公司认为有三种异常类型:

    • 受查异常(Checked Exception)
    • 非受查异常(UnChecked Exception)
    • 错误(Error)

    1.5 受查和非受查异常之间的区别

    1)受查异常

    除了RuntimeExceptionError外,继承自Throwable类的类称为受查异常,例如:IOException、SQLException 等。受查异常在编译时进行检查。

    常见的有以下几个方面:

    • 试图在文件尾部后面读取数据
    • 试图打开一个不存在的文件
    • 试图根据给定的字符串查找Class对象,而这个字符串表示的类并不存在

    2)非受查异常

    继承自RuntimeException类的异常被称为非受查异常,例如:ArithmeticException、 NullPointerException、 ArrayIndexOutOfBoundsException 等。非受查异常不会在编译时检查,而是在运行时进行检查。

    常见的有以下几个方面:

    • 错误的类型转换
    • 数组访问越界
    • 访问null指针

    “如果出现了RuntimeException异常,那么一定是你自身的问题”,是一条相当有道理的规则。

    3)错误(Error)

    错误是一种无法恢复的异常类型,通常是在java运行时系统的内部错误和资源耗尽错误。应用程序不应该抛出这种类型的对象。如果出现了这样的内部错误,除了通告给用户,并尽力的使得程序安全的终止之外,再也无能为力了。这种情况很少出现。

    1.6 可能出现异常的常见场景

    1)发生ArithmeticException的场景

    如果我们将任何数字除以0,就会出现一个 ArithmeticException 异常。

    int a = 50/0;//ArithmeticException  

    2)发生NullPointerException的场景

    如果变量的值为null,那么调用此变量将会出现 NullPointerException 异常。

    String s = null;  
    System.out.println(s.length());//NullPointerException  

    3)发生NumberFormatException的场景

    任何值的格式错误,都有肯能发生 NumberFormatException 异常。假设一个字符串变量,其中包含了字符,若将此变量转换为数字类型,将会发生 NumberFormatException 异常。

    String s = "abc";  
    int i = Integer.parseInt(s);//NumberFormatException

    4)发生ArrayIndexOutOfBoundsException的场景

    如果你在一个不存在的的数组索引中插入任何值,则会导致 ArrayIndexOutOfBoundsException 异常。

    int a[] = new int[5];  
    a[10] = 50; //ArrayIndexOutOfBoundsException  

    1.7 Java 异常处理关键字

    下面是 Java 异常处理中的5个关键字:

    trycatchfinallythrowthrows

    1.8 创建自定义异常类

    在程序中,可能会遇到任何标准异常类都没有能够充分地描述清楚的问题。在这种情况下,创建自己的异常类就是一件顺理成章的事情了。我们需要做的只是定义一个派生于 Exception 的类,或者派生于 Exception 子类的类。例如,定义一个派生于 IOException 的类。

    习惯上,定义的类应该包含两个构造器,一个是默认构造器,一个是描述详细信息的的构造器(超类 Throwable 的 toString 方法将会打印出这些详细信息,这在调试中非常有用。)

    示例如下:

    class FileFormatException extends IOException {
        public FileFormatException() {}
        public FileFormatException(String gripe) {
            super(gripe);
        }
    }

    现在,就可以抛出自己定义的异常类型了。

    String readData(BufferedReader in) throws FileFormatException {
        ...
        while (...) {
            // EOF encountered
            if (ch == -1) {
                if (n < len)
                    throw new FileFormatException();
            }
            ...
        }
        return s;
    }

    2. Java try-catch

    将可能发生异常的代码放在try块中,且必须在方法中才能使用。try 块后必须使用catch块或finally块。

    2.1 Java try 块

    1)try-catch 语法

    try{  
    // 可能抛出异常的代码
    }catch(Exception_class_Name ref){} 

    2)try-finally 语法

    try{  
    // 可能抛出异常的代码
    }finally{}  

    2.2 Java catch 块

    Java catch块被用于处理异常,必须在try块后使用。

    你可以在一个try块后使用多个catch

    2.3 未使用异常处理的问题

    如果我们不使用try-catch处理异常,看看会发生什么。

    public class Testtrycatch1 {  
        public static void main(String args[]) {  
            int data=50/0;// 可能抛出异常
            System.out.println("代码的其余部分...");  
        }  
    }  

    输出:

    Exception in thread main java.lang.ArithmeticException:/ by zero

    如上面的示例所示,代码的其余部分并没有执行。("代码的其余部分..."未打印)

    2.4 使用异常处理解决问题

    让我们通过try-catch块来查看上述问题的解决方案。

    public class Testtrycatch2 {  
        public static void main(String args[]) {  
    
            try {  
                int data = 50/0;  
            }
            catch(ArithmeticException e) {
                System.out.println(e);
            }  
    
            System.out.println("代码的其余部分...");  
        }  
    }  

    输出:

    Exception in thread main java.lang.ArithmeticException:/ by zero
    代码的其余部分...

    3. 使用多个 catch 块

    如果需要在发生不同异常时执行不同的任务,则需要使用多个 catch 块。

    查看下面一个简单的多 catch 块示例。

    public class TestMultipleCatchBlock{  
        public static void main(String args[]) {  
    
            try{  
                int a[] = new int[5];  
                a[5] = 30/0;  
            }  
            catch(ArithmeticException e) {
                System.out.println("任务1已完成");
            }  
            catch(ArrayIndexOutOfBoundsException e) {
                System.out.println("任务2已完成");
            }  
            catch(Exception e) {
                System.out.println("已完成通用任务");
            }
    
            System.out.println("代码的其余部分...");  
    
        }  
    }  

    输出:

    任务1已完成
    代码的其余部分...

    规则:一次只有一个异常发生,并且一次只执行一个catch块。

    规则: 所有异常必须从最具体到最通用的顺序排序,即捕获ArithmeticException必须在捕获Exception之前发生。

    4. Java 嵌套 try 块

    Java try块中的try块被称为try嵌套块。

    4.1 为什么使用 try 嵌套块?

    有时可能会出现一种情况,一个块的某个部分可能导致一个错误,而整个块的本身可能会导致另一个错误。在这种情况下,必须使用嵌套异常处理程序。

    语法:

    ...  
    try  
    {  
        statement 1;  
        statement 2;  
        try  
        {  
            statement 1;  
            statement 2;  
        }  
        catch(Exception e)  
        {  
            ...
        }  
    }  
    catch(Exception e) {...}  
    ....  

    5. Java finally 块

    Java finally 块是用来执行重要代码的块(如关闭连接、流等)。

    无论是否处理异常,最终都会执行 finally 块。

    注意:无论你是否处理异常,在终止程序之前,JVM都将执行finally块(如果存在的话)

    5.1 为什么要使用 finally 块

    finally 块可以用于放置"clear"代码,例如关闭文件,关闭连接等。

    6. Java 抛出异常

    6.1 Java throw 关键字

    Java throw 关键字用于显示的抛出异常。

    我们可以使用 throw 关键字在 Java 中抛出检查(Checked)或未检查(UnChecked)异常。throw 关键字主要用于抛出自定义异常。

    Java throw 语法如下:

    throw exception;  

    7. Java throws 关键字

    Java throws 关键字被用于声明一个异常。它给程序员提供了一个信息,说明可能会发生异常,所以程序员最好提供异常处理代码,以保证程序正常的流程。

    异常处理主要用于处理受查异常,如果出现任何非受查异常,如"NullPointerException",都是程序员自身的错误,请认真检查你的代码。

    7.1 Java throws 语法

    return_type method_name() throws exception_class_name {  
        // method code  
    }  

    8.2 应该声明哪个异常?

    仅仅声明受查异常,因为:

    • 非受查异常:程序员应该更正代码以确保代码正确无误。
    • Error:无法控制,如果出现了 VirtualMachineErrorStackOverflowError等异常,将无法进行任何操作。

    8.3 Java throws 优势

    使用 throws 声明受查异常后,使得受查异常可以在调用堆栈中进行(传递)转发。它向处理该异常的方法提供异常信息。

    9. 异常处理方法的重写

    关于重写异常处理方法的规则如下:

    • 超类方法没有声明异常:
      如果超类方法没有声明异常,则子类重写方法不能声明受查异常,但可以声明非受查异常。
    • 超类方法声明了异常:
      如果超类方法声明了异常,则子类重写方法可以声明与超类方法相同的异常,也可以不声明异常。若父类方法声明父类异常,子类重写方法声明子类异常也可以,反之不可以。

    规则:一次只有一个异常发生,并且一次只执行一个catch块。

    规则: 所有异常必须从最具体到最通用的顺序排序,即捕获ArithmeticException必须在捕获Exception之前发生。

  • 相关阅读:
    注意:开发环境不同,启动代码不同…
    6410在rvds下编译启动代码报错分析
    S3C6410的启动代码分析&nbsp;一
    s3c6410开发板LED驱动程序设计详细…
    季逸超:90后IT少年的“盖茨梦”
    我的博客今天0岁52天了,我领取了…
    在linux中获取错误返回信息&nbsp;&amp;…
    各种居中对齐
    文本对齐方式
    素描人像
  • 原文地址:https://www.cnblogs.com/deityjian/p/11424933.html
Copyright © 2011-2022 走看看