14.异常

异常

概述

异常: 程序出现的不正常情况

异常体系:

image-20201014160253543

  • Error: 严重问题, 不需要处理
  • Exception: 称为异常类, 表示程序本身可以处理的问题
    • RuntimeException: 在编译期不检查的异常, 出问题后, 需要修改代码
    • 非RuntimeException: 编译期就必须处理掉的, 否则程序不能通过编译, 就更不能正常运行了

JVM默认处理方法

如果程序出了问题,代码没有做处理, JVM会默认处理

  • 输出异常的名称, 异常原因及异常出现的位置信息在控制台
  • 程序停止执行

demo

package exception;

public class DefaultDeal {
    public static void main(String[] args) {
        System.out.println("start");
        method();
        System.out.println("end");
    }

    public static void method() {
        int[] arr = {1, 2, 3};
        System.out.println(arr[3]);
    }
    /*
    Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: Index 3 out of bounds for length 3
        at exception.DefaultDeal.method(DefaultDeal.java:12)
        at exception.DefaultDeal.main(DefaultDeal.java:6)
     */
}

异常处理

格式

try {
	可以出现异常的代码;
} catch (异常名 变量名) {
	异常处理代码;
}

Demo

package exception;

public class TryCatch {
    public static void main(String[] args) {
        System.out.println("start");
        method();
        System.out.println("end");
    }

    public static void method() {
        try {
            int[] arr = {1, 2, 3};
            System.out.println(arr[3]);
        } catch (ArrayIndexOutOfBoundsException e) {
            // System.out.println("数组索引越界");
            e.printStackTrace();
        }
    }
}

Throwable成员方法

方法名 说明
public String getMessage() 返回此 throwable的详细消息字符串
public String toString() 返回此可抛出的简短描述
public void printStackTrace() 把异常的错误信息输出在控制台

demo

package exception;

public class ThrowableDemo {
    public static void main(String[] args) {
        System.out.println("start");
        method();
        System.out.println("end");
    }

    public static void method() {
        try {
            int[] arr = {1, 2, 3};
            System.out.println(arr[3]);
        } catch (ArrayIndexOutOfBoundsException e) {
            // e.printStackTrace();
            System.out.println(e.getMessage());  // Index 3 out of bounds for length 3
            System.out.println(e.toString());  // java.lang.ArrayIndexOutOfBoundsException: Index 3 out of bounds for length 3
        }
    }
}

编译时异常和运行异常

java异常类分为两大类: 编译时异常和运行时异常, 也被称为受检异常和非受检异常

所有RuntimeException类及其子类称为运行时异常, 其他的异常都是编译时异常

  • 编译时异常: 必须显示处理, 否则程序就会发生错误, 无法通过编译
  • 运行时异常: 无需显示处理, 也可以和编译是异常一样处理

Demo

package exception;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;

public class CompileRuntimeException {
    public static void main(String[] args) {
        System.out.println("start");
        method();
        method2();
        System.out.println("end");
    }

    // 运行时异常: 运行时程序逻辑处理抛出的问题
    public static void method() {
        int [] arr = {1, 2, 3};
        System.out.println(arr[3]);
    }

    // 编译时异常: 编译过程中程序判断可能出问题
    public static void method2() {
        try {
            String s = "2020-08-09";
            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
            Date d = sdf.parse(s);
            System.out.println(d);
        } catch (ParseException e) {
            e.printStackTrace();
        }
    }
}

throws处理异常

针对一些没有权限进行异常的处理, java提供了throws处理方法

格式

throws 异常类名;

注意: 格式跟在方法括号后面

  • 编译时异常必须进行处理: 两种处理方法: try...catch...或者throws, 如果采取throws方案, 将来谁调用谁处理
  • 运行时异常可以不处理: 出问题后需要回来修改代码

demo

package exception;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;

public class ThrowsDemo {
    public static void main(String[] args) {
        System.out.println("start");
        // method();
        try {
            method2();
        } catch (ParseException e) {
            e.printStackTrace();
        }
        System.out.println("end");
    }

    // 运行时异常: 运行时程序逻辑处理抛出的问题
    /*
    public static void method() throws ArrayIndexOutOfBoundsException {
        int [] arr = {1, 2, 3};
        System.out.println(arr[3]);
    }
     */

    // 编译时异常: 编译过程中程序判断可能出问题

    public static void method2() throws ParseException {
        String s = "2020-08-09";
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        Date d = sdf.parse(s);
        System.out.println(d);
    }
}

自定义异常 throw

格式

public class 异常类名 extends Exception {
	无参构造
	带参构造
}

范例

public class ScoreException extends Exception {
	public ScoreException() {}
	public ScoreException(String message) {
		super(message);
	}
}

示例

ScoreException

package exception.customException;

public class ScoreException extends Exception {
    public ScoreException() {}
    public ScoreException(String message) {
        super(message);
    }
}

Teacher

package exception.customException;

public class Teacher {
    public void checkSrore(int score) throws ScoreException {
        if(score<0 || score>100) {
            // throw new ScoreException();
             throw new ScoreException("分数有误, 范围应该在0~100");
        } else {
            System.out.println("正常分数");
        }
    }
}

Demo

package exception.customException;

import java.util.Scanner;

public class Demo {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        System.out.println("请输入分数;");
        int score = sc.nextInt();

        Teacher t = new Teacher();
        try {
            t.checkSrore(score);
        } catch (ScoreException e) {
            e.printStackTrace();
        }
    }
}




throws和throw区别

throws

  • 用在方法声明后面, 跟的是异常类名
  • 表示抛出异常, 由该方法的调用者来处理
  • 表示出现异常的一种可能性, 并不一定会发成这些异常

throw

  • 用在方法体内, 跟的是异常对象名

  • 表示抛出异常,有方法体内的语句处理

  • 指定throw一定抛出了某种异常

原文地址:https://www.cnblogs.com/ryxiong-blog/p/13890429.html