异常是程序中的一些错误,但并非全部的错误都是异常,而且错误有时候是能够避免的。java
好比说,你的代码少了一个分号,那么运行出来结果是提示是错误 java.lang.Error;若是你用System.out.println(11/0),那么你是由于你用0作了除数,会抛出 java.lang.ArithmeticException 的异常。程序员
异常发生的缘由有不少,一般包含如下几大类:网络
这些异常有的是由于用户错误引发,有的是程序错误引发的,还有其它一些是由于物理错误引发的。-this
要理解Java异常处理是如何工做的,你须要掌握如下三种类型的异常:spa
全部的异常类是从 java.lang.Exception 类继承的子类。blog
Exception 类是 Throwable 类的子类。除了Exception类外,Throwable还有一个子类Error 。继承
Java 程序一般不捕获错误。错误通常发生在严重故障时,它们在Java程序处理的范畴以外。three
Error 用来指示运行时环境发生的错误。内存
例如,JVM 内存溢出。通常地,程序不会从错误中恢复。ci
异常类有两个主要的子类:IOException 类和 RuntimeException 类。
在 Java 内置类中(接下来会说明),有大部分经常使用检查性和非检查性异常。
使用 try 和 catch 关键字能够捕获异常。try/catch 代码块放在异常可能发生的地方。
try/catch代码块中的代码称为保护代码,使用 try/catch 的语法以下:
Catch 语句包含要捕获异常类型的声明。当保护代码块中发生一个异常时,try 后面的 catch 块就会被检查。
若是发生的异常包含在 catch 块中,异常会被传递到该 catch 块,这和传递一个参数到方法是同样。
// 文件名 : ExcepTest.java import java.io.*; public class ExcepTest{ public static void main(String args[]){ try{ int a[] = new int[2]; System.out.println("Access element three :" + a[3]); }catch(ArrayIndexOutOfBoundsException e){ System.out.println("Exception thrown :" + e); } System.out.println("Out of the block"); } } 结果: Exception thrown :java.lang.ArrayIndexOutOfBoundsException: 3 Out of the block
一个 try 代码块后面跟随多个 catch 代码块的状况就叫多重捕获。
多重捕获块的语法以下所示:
try{ // 程序代码 }catch(异常类型1 异常的变量名1){ // 程序代码 }catch(异常类型2 异常的变量名2){ // 程序代码 }catch(异常类型2 异常的变量名2){ // 程序代码 }
上面的代码段包含了 3 个 catch块。
能够在 try 语句后面添加任意数量的 catch 块。
若是保护代码中发生异常,异常被抛给第一个 catch 块。
若是抛出异常的数据类型与 ExceptionType1 匹配,它在这里就会被捕获。
若是不匹配,它会被传递给第二个 catch 块。
如此,直到异常被捕获或者经过全部的 catch 块。
该实例展现了怎么使用多重 try/catch。
try { file = new FileInputStream(fileName); x = (byte) file.read(); } catch(FileNotFoundException f) { // Not valid! f.printStackTrace(); return -1; } catch(IOException i) { i.printStackTrace(); return -1; }
若是一个方法没有捕获到一个检查性异常,那么该方法必须使用 throws 关键字来声明。throws 关键字放在方法签名的尾部。
也可使用 throw 关键字抛出一个异常,不管它是新实例化的仍是刚捕获到的。
下面方法的声明抛出一个 RemoteException 异常:
一个方法能够声明抛出多个异常,多个异常之间用逗号隔开。
例如,下面的方法声明抛出 RemoteException 和 InsufficientFundsException:
import java.io.*; public class className { public void withdraw(double amount) throws RemoteException, InsufficientFundsException { // Method implementation } //Remainder of class definition }
finally 关键字用来建立在 try 代码块后面执行的代码块。
不管是否发生异常,finally 代码块中的代码总会被执行。
在 finally 代码块中,能够运行清理类型等收尾善后性质的语句。
finally 代码块出如今 catch 代码块最后,
public class ExcepTest{ public static void main(String args[]){ int a[] = new int[2]; try{ System.out.println("Access element three :" + a[3]); }catch(ArrayIndexOutOfBoundsException e){ System.out.println("Exception thrown :" + e); } finally{ a[0] = 6; System.out.println("First element value: " +a[0]); System.out.println("The finally statement is executed"); } } }
结果:
Exception thrown :java.lang.ArrayIndexOutOfBoundsException: 3 First element value: 6 The finally statement is executed
注意下面事项:
在 Java 中你能够自定义异常。编写本身的异常类时须要记住下面的几点。
只继承Exception 类来建立的异常类是检查性异常类。
下面的 InsufficientFundsException 类是用户定义的异常类,它继承自 Exception。
一个异常类和其它任何类同样,包含有变量和方法。
如下实例是一个银行帐户的模拟,经过银行卡的号码完成识别,能够进行存钱和取钱的操做。
// 文件名InsufficientFundsException.java import java.io.*; //自定义异常类,继承Exception类 public class InsufficientFundsException extends Exception { //此处的amount用来储存当出现异常(取出钱多于余额时)所缺少的钱 private double amount; public InsufficientFundsException(double amount) { this.amount = amount; } public double getAmount() { return amount; } }
在下面的 CheckingAccount 类中包含一个 withdraw() 方法抛出一个 InsufficientFundsException 异常。
import java.io.*; //此类模拟银行帐户 public class CheckingAccount { //balance为余额,number为卡号 private double balance; private int number; public CheckingAccount(int number) { this.number = number; } //方法:存钱 public void deposit(double amount) { balance += amount; } //方法:取钱 public void withdraw(double amount) throws InsufficientFundsException { if(amount <= balance) { balance -= amount; } else { double needs = amount - balance; throw new InsufficientFundsException(needs); } } //方法:返回余额 public double getBalance() { return balance; } //方法:返回卡号 public int getNumber() { return number; } }
下面的 BankDemo 程序示范了如何调用 CheckingAccount 类的 deposit() 和 withdraw() 方法。
public class BankDemo { public static void main(String [] args) { CheckingAccount c = new CheckingAccount(101); System.out.println("Depositing $500..."); c.deposit(500.00); try { System.out.println("\nWithdrawing $100..."); c.withdraw(100.00); System.out.println("\nWithdrawing $600..."); c.withdraw(600.00); }catch(InsufficientFundsException e) { System.out.println("Sorry, but you are short $" + e.getAmount()); e.printStackTrace(); } } }
编译上面三个文件,并运行程序 BankDemo,获得结果以下所示:
Depositing $500... Withdrawing $100... Withdrawing $600... Sorry, but you are short $200.0 InsufficientFundsException at CheckingAccount.withdraw(CheckingAccount.java:25) at BankDemo.main(BankDemo.java:13)
在Java中定义了两种类型的异常和错误。