Java异常
在Java语言中,将程序执行中发生的不正常情况称为“异常”。 (开发过程中的语法错误和逻辑错误不是异常)
Java程序在执行过程中所发生的异常事件可分为两类:
Error
:Java虚拟机无法解决的严重问题。如:JVM系统内部错误、资源耗尽等严重情况。比如:StackOverflowError和OOM。一般不编写针对性的代码进行处理。Exception
: 其它因编程错误或偶然的外在因素导致的一般性问题,可以使用针对性的代码进行处理。例如:
对于这些错误,一般有两种解决方法:
捕获错误最理想的是在编译期间
,但有的错误只有在运行时才会发生
运行时异常:
java.lang.RuntimeException
类及其子 类都是运行时异常。编译时异常:
是指编译器要求必须处置的异常。即程序在运行时由于外界因素造成的一般性异常。编译器要求Java程序必须捕获或声明所有编译时异常。
对于这类异常,如果程序不处理,可能会带来意想不到的结果
java.lang.Throwable
java.lang.Error
: 一般不编写针对性的代码进行处理,只能通过改代码,例如:栈溢出StackOverflowError、堆溢出OutOfMemoryError
java.lang.Exception
: 可以进行异常的处理
编译时/检查型异常(checked)
运行时/非检查型异常(unchecked,RuntimeException)
从程序执行过程,看编译时异常和运行时异常
编译时异常:执行javac.exe命名时,可能出现的异常
运行时异常:执行java.exe命名时,出现的异常
//******************以下是运行时异常***************************
//ArithmeticException 算术异常
@Test
public void test6(){
int a = 10;
int b = 0;
System.out.println(a / b);
}
//InputMismatchException 输入异常
@Test
public void test5(){
Scanner scanner = new Scanner(System.in);
int score = scanner.nextInt();
System.out.println(score);
scanner.close();
}
//NumberFormatException 数值转换异常
@Test
public void test4(){
String str = "123";
str = "abc";
int num = Integer.parseInt(str);
}
//ClassCastException 类型转换异常
@Test
public void test3(){
Object obj = new Date();
String str = (String)obj;
}
//IndexOutOfBoundsException 角标越界异常
@Test
public void test2(){
//ArrayIndexOutOfBoundsException
// int[] arr = new int[10];
// System.out.println(arr[10]);
//StringIndexOutOfBoundsException
String str = "abc";
System.out.println(str.charAt(3));
}
//NullPointerException 空指针异常
@Test
public void test1(){
// int[] arr = null;
// System.out.println(arr[3]);
String str = "abc";
str = null;
System.out.println(str.charAt(0));
}
//******************以下是编译时异常***************************
@Test
public void test7(){
// File file = new File("hello.txt");
// FileInputStream fis = new FileInputStream(file);
//
// int data = fis.read();
// while(data != -1){
// System.out.print((char)data);
// data = fis.read();
// }
//
// fis.close();
}
在编写程序时,经常要在可能出现错误的地方加上检测的代码, 如进行x/y运算时,要检测分母为0,数据为空,输入的不是数据 而是字符等。过多的if-else分支会导致程序的代码加长、臃肿, 可读性差。因此采用异常处理机制。
Java采用的异常处理机制,是将异常处理的程序代码集中在一起, 与正常的程序代码分开,使得程序简洁、优雅,并易于维护
可以理解为异常的处理方式:
① try-catch-finally
② throws
try{
//可能出现异常的代码
}catch(异常类型1 变量名1){
//处理异常的方式1
}catch(异常类型2 变量名2){
//处理异常的方式2
}catch(异常类型3 变量名3){
//处理异常的方式3
}
....
finally{
//一定会执行的代码
}
try
捕获异常的第一步是用try{…}语句块选定捕获异常的范围,将可能出现异常的代码放在try语句块中。
catch
(Exceptiontype e)在catch语句块中是对异常对象进行处理的代码。每个try语句块可以伴随一个或多个catch语句,用于处理可能产生的不同类型的异常对象
如果明确知道产生的是何种异常,可以用该异常类作为catch的参数;也可以用其父类作为catch的参数。
比 如 : 可 以 用 ArithmeticException 类 作 为 参 数 的 地 方 , 就 可 以 用RuntimeException类作为参数,或者用所有异常的父类Exception类作为参数。但不能是与ArithmeticException类无关的异常,如NullPointerException(catch中的语句将不会执行)。
finally
捕获异常的最后一步是通过finally语句为异常处理提供一个统一的出口,使得在控制流转到程序的其它部分以前,能够对程序的状态作统一的管理。
像数据库连接、输入输出流、网络编程Socket等资源,JVM是不能自动的回收的,我们需要自己手动的进行资源的释放。此时的资源释放,就需要声明在finally中。
不论在try代码块中是否发生了异常事件,catch语句是否执行,catch语句是否有异常,catch语句中是否有return,finally块中的语句都会被执行
throws方式也称声明抛出异常,声明抛出异常是Java中处理异常的第二种方式
public void readFile(String file) throws FileNotFoundException {
//...
// 读文件的操作可能产生FileNotFoundException类型的异常
FileInputStream fis = new FileInputStream(file);
//...
}
在程序执行中,除了自动抛出异常对象的情况之外,我们还可以手动的throw一个异常类的对象。
throw 和 throws区别:
throw 表示生成并抛出一个异常类的对象,声明在方法体内。
throws 属于异常处理的一种方式,声明在方法的声明处。
class Student{
private int id;
public void regist(int id) throws Exception {
if(id > 0){
this.id = id;
}else{
//手动抛出异常对象
throw new Exception("您输入的数据非法!");
}
}
@Override
public String toString() {
return "Student [id=" + id + "]";
}
}
若手动抛出的是Exception,Exception包括编译时和运行时异常,编译时异常必须及时处理,所以需要在方法名处用
throws
处理异常
public class MyException extends Exception{
static final long serialVersionUID = -7034897193246939L;
public MyException(){
}
public MyException(String msg){
super(msg);
}
}
原文:https://www.cnblogs.com/silloutte/p/14643213.html