java中所有错误的超类为:Throwable。有两个子类:Error和Exception
Error的子类描述的都是系统错误,比如虚拟机内存溢出
Exception的子类描述的都是程序错误,比如空指针,下标越界
异常处理机制中的try-catch语法
try{
可能出现异常的代码段
}catch(XXXException e){
try语句块中出现XXXException后的处理代码
}
try语句不能单独写,后面必须跟catch或finally
try语句中出错代码以下的内容不会被执行
public class TryCatchDemo {
public static void main(String[] args) {
System.out.println("程序开始了...");
try {
String str = "abc";
System.out.println(str.length());
System.out.println(str.charAt(0));
System.out.println(Integer.parseInt(str));
System.out.println("!!!!!!");
}catch (NullPointerException | StringIndexOutOfBoundsException e) {
System.out.println("出现了空指针或字符串下标越界异常!");
}catch (Exception e) {
System.out.println("反正就是出个错!");
}
System.out.println("程序结束了...");
}
}
输出结果为
“!!!!!!”没有输出
可以用多个catch,且catch可以用“|”来合并
fianllyfinally块是异常处理机制的最后一块,它可以直接跟在try语句块之后或者最后一个catch块之后
只要程序执行到try语句块,无论try中代码是否出现异常,最终fianlly都必定执行,通常我们会将释放资源这类 *** 作放到finally中确保执行
public class FinallyDemo {
public static void main(String[] args) {
System.out.println("程序开始了");
try{
// String str = null;
String str = "abc";
System.out.println(str.length());
return;
}catch(Exception e){
System.out.println("出现了错误");
}finally{
System.out.println("finally中的代码执行了!");
}
System.out.println("程序结束了");
}
}
throw
throw关键字可以主动对外抛出一个异常实例,通常下列两种情况需要:
- 当前代码片段出现了异常,但是该异常不应当在当前代码片段执行,所以对外抛出
- 当前程序出现了满足语法,但是不满足业务场景时,也可以当做异常抛出。例如:输入用户年龄为10000岁,这不符合正常现象,所以将这当做与异常抛出
public class Person { private int age; public int getAge() { return age; } public void setAge(int age) throws Exception { if(age<0||age>100){ // throw new RuntimeException("年龄超过了范围!"); /* 当我们使用throw主动抛出一个异常时,就必须在方法上使用throws声明该异常的抛出通知调用者 处理该异常。RuntimeException是一个例外。 */ throw new Exception("年龄超过了范围!"); } this.age = age; } }
throwspublic class ThrowDemo { public static void main(String[] args) { Person p = new Person(); try { /* 当我们调用一个含有throws声明异常抛出的方法时,编译器要求我们必须处理该异常 处理方式有两种可选: 1:可使用try-catch捕获该异常(当前代码的演示) 2:可以在当前方法上继续使用throws声明将异常抛出 实际情况应当结合实际的业务场景分析决定。 */ p.setAge(10000);//满足语法不满足业务 } catch (Exception e) { e.printStackTrace(); } System.out.println("我今年:"+p.getAge()+"岁"); } }
子类在重写超类中含有throws声明异常抛出的方法时对throws的重写规则
public class ThrowsDemo {
public void dosome()throws IOException, AWTException {}
}
class SubClass extends ThrowsDemo{
// public void dosome()throws IOException, AWTException {}
//允许子类方法不再抛出任何异常
// public void dosome(){}
//允许子类方法抛出部分异常
// public void dosome()throws IOException{}
//允许子类方法抛出超类方法声明异常的子类型异常
// public void dosome()throws FileNotFoundException {}
//不允许子类抛出额外异常(超类方法上没有的且没有继承关系的异常)
// public void dosome()throws SQLException {}
//不允许子类抛出比超类方法声明的异常还大的异常
// public void dosome()throws Exception {}
}
即子类重写超类中含有throws声明异常抛出的方法时,子类可以不抛出异常,也可以抛出(父类所抛出异常)的子类或者本身,不能抛出(父类抛出异常)的父类或者与(父类抛出异常)不相关的异常。
要注意的是:非检查异常RuntimeException异常可以在子类抛出,RuntimeException的子类有NullPointException,IndexOutOfBounds等
try-catch改进原本的异常处理机制在IO中的应用方式
import java.io.FileOutputStream;
import java.io.IOException;
public class FinallyDemo2 {
public static void main(String[] args) {
FileOutputStream fos = null;
try {
fos = new FileOutputStream("fos.dat");
fos.write(1);
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
if (fos != null) {
fos.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
JDK7之后,java推出了一个新的特性:自动关闭
语法
try(
定义并初始化需要在finally中调用close关闭的类实例
){
}catch(XXXException e){
}
public class AutoCloseableDemo {
public static void main(String[] args) {
try(
//只有实现了AutoCloseable接口的类才可以在这里定义,并最终编译器会改为在finally中调用close()
//编译后的代码参照FinallyDemo2的样子
FileOutputStream fos = new FileOutputStream("fos.dat");
//String没有实现该接口,不能在这里定义
// String str = "abc";
){
fos.write(1);
} catch (IOException e) {
e.printStackTrace();
}
}
}
输入输出流都可以在try()中定义,并且会将它自动关闭,不用在finally人工关闭
fianlly 题目分析public class FinallyDemo3 {
public static void main(String[] args) {
System.out.println(
test("0")+","+test(null)+","+test("")
);
}
public static int test(String str){
try{
return str.charAt(0) - '0';
}catch(NullPointerException e){
return 1;
}catch(Exception e){
return 2;
}finally {
return 3;
}
}
}
结果为3,3,3
分析:
在调用test("0")时,系统会先设一个return有关的值,即因为test的返回值为int,所以设一个int型的变量a,用于存储test的返回值。所以,调用test("0")时,先进行try语句块,得到值为0,就将0赋给变量a,由于一旦执行了try语句块,就必须执行finally语句块,所以,就将3的值赋给a,所以返回值为3,后面两个同理。
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)