18.Java异常

Java异常

Java 中的异常(Exception)又称为例外,是一个在程序执行期间发生的事件,它中断正在执行程序的正常指令流。为了能够及时有效地处理程序中的运行错误,Java中引入了异常类的概念。异常类的引入即明确了程序在执行过程中发生的什么问题,又提供类针对异常进行处理的解决方案。
在这里插入图片描述
Error:是程序中无法处理的错误,表示运行应用程序中出现了严重的错误。此类错误一般表示代码运行时JVM出现问题。通常有Virtual MachineError(虚拟机运行错误)、NoClassDefFoundError(类定义错误)等。比如说当jvm耗完可用内存时,将出现OutOfMemoryError。此类错误发生时,JVM将终止线程。非代码性错误。因此,当此类错误发生时,应用不应该去处理此类错误。

Exception::程序本身可以捕获并且可以处理的异常(包括自定义异常)。

运行时异常(不受检异常):RuntimeException类极其子类表示JVM在运行期间可能出现的错误。编译器不会检查此类异常,并且不要求处理异常,比如用空值对象的引用(NullPointerException)、数组下标越界(ArrayIndexOutBoundException)。此类异常属于不可查异常,一般是由程序逻辑错误引起的,在程序中可以选择捕获处理,也可以不处理。

非运行时异常(受检异常):Exception中除RuntimeException极其子类之外的异常。编译器会检查此类异常,如果程序中出现此类异常,比如说IOException,必须对该异常进行处理,要么使用try-catch捕获,要么使用throws语句抛出,否则编译不通过。包括我们在编写代码时的一些错误,无法通过编译的代码,称谓编译期异常,也属于非运行时异常。

异常产生的原因

在 Java 中一个异常的产生,主要有如下三种原因:

  • Java 内部错误发生异常,Java 虚拟机产生的异常。
  • 编写的程序代码中的错误所产生的异常,例如空指针异常、数组越界异常等。这种异常称为未检査的异常,一般需要在某些类中集中处理这些异常。
  • 手动生成的异常,这种异常称为检査的异常,一般用来告知该方法的调用者一些必要的信息。

异常的处理方式

捕获异常:try,catch,finally

try {
   ... 
} catch (Exception e) {
    ... 
} finally {
    ... 
}


  • try代码块:监视代码执行过程,如果代码发生异常,则跳转到catch代码块进行处理。
  • catch代码块:可选执行代码块,如果try代码块未发生异常,则不会被执行。并且一个try代码块可以跟随多个catch代码块,根据不同的Exception处理不同的异常,这种情况称之为多重捕获。
  • finally代码块:不论try代码块是否发生异常,finally代码块都会被执行,通常用于处理工作。

抛出异常:throws

Java允许在方法的后面使用throws关键字对外声明该方法有可能发生异常,这样调用者在调用方法时,就明确地知道该方法有异常,并且必须在程序中对异常进行处理,否则编译无法通过。
程序员在写代码时,可能预感到会发生异常,那么会手动抛出一个异常,交由使用者去处理

public static void main(String[] args) {
		TryTest t=new TryTest();
		double d=t.chu(4,2);
		System.out.printLn(d);
	}
	public double chu(double a,double b)throws Exception{
		return a/b;
	}

如果方法被调用方法抛出一个异常,那么调用者会出现编译错误,无法执行。需要修改成为:

public static void main(String[] args) {
		TryTest t=new TryTest();
		double d=0;
		try {
			d = t.chu(4,2);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		System.out.println(d);
	}
	public double chu(double a,double b)throws Exception{
		return a/b;
	}

当方法抛出一个异常时,调用者要么使用try代码块进行捕获,要么继续在本方法上抛出异常,由后续的调用者去处理。

声明异常:throw

如果需要在程序中自行抛出异常,则应使用 throw 语句,throw 语句可以单独使用,throw 语句抛出的不是异常类,而是一个异常实例,而且每次只能抛出一个异常实例。当 Java 运行时接收到开发者自行抛出的异常时,会中止当前的执行流,跳到该异常对应的 catch 块来处理该异常。即不管是系统自动抛出的异常还是程序员手动抛出的异常,Java 运行时环境对异常的处理没有任何差异。
如果 throw 语句抛出的异常是 Checked 异常,则该 throw 语句要么处于 try 块里,显式捕获该异常,要么放在一个带 throws 声明抛出的方法中,即把该异常交给该方法的调用者处理;
如果 throw 语句抛出的异常是 Runtime 异常,则该语句无须放在 try 块里,也无须放在带 throws 声明抛出的方法中;程序既可以显式使用 try…catch来捕获并处理该异常,也可以完全不理会该异常,把该异常交给该方法调用者处理。

public static void main(String[] args) {
		TryTest t = new TryTest();
		try {
		double d = t.chu(4, 0);
		System.out.println(d);
		}catch (Exception e) {
			System.out.println("0不能做除数");
		}
	}

	public double chu(double a, double b) {
		if(b==0) {
			throw new RuntimeException();
		}
		return a / b;
	}

常见异常

在这里插入图片描述

自定义异常

在程序开发中,可能会遇到程序特有的问题,那么程序员在处理这些特有的问题时,一般会自定义一些异常来使用,这样既能保证程序的安全性和稳定性,又能给出较为友好的提示,以便于使用。

异常可以继承的类

  • 继承Throwable类
  • 继承Exception类
  • 继承RunTimeException类

一般会选择继承Exception和RuntimeException,如果不要求调用者一定要处理抛出的异常,就继承RuntimeException。

public class NumberIsZoraException extends Exception{

	public NumberIsZoraException(String msg) {
		super(msg);
	}
}

public static void main(String[] args) {
		TryTest t = new TryTest();
		double d=0;
		try {
			d = t.chu(4, 0);
		} catch (NumberIsZoraException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}

	public double chu(double a, double b) throws NumberIsZoraException {
		if(b==0) {
			throw new NumberIsZoraException("除数不能为0");
		}
		return a / b;
	}

在这里插入图片描述

异常的使用原则

java的异常处理涉及到程序流程的跳转,所以虚拟机需要保存程序的执行流程,以便异常发生时能正确的跳转,这也就导致了使用异常时会引起额外的开销,所以,要谨慎地使用异常。
使用异常有如下几个原则:
1、尽量避免使用异常,将异常情况提前检测出来。
2、不要为每个可能会出现异常的语句都设置try和catch。
3、避免在方法中抛出(throw)或者捕获(catch)运行时异常RuntimeException和Error。
4、避免总是catch Exception或Throwable,而要catch具体的异常类。这样可以使程序更加清晰。
5、不要压制、隐瞒异常。将不能处理的异常往外抛,而不是捕获之后随便处理。
6、不要在循环中使用try…catch,尽量将try…catch放在循环外或者避免使用。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值