异常处理:
异常:阻止当前方法或作用域继续执行的问题,在程序中导致程序中断的一些指令。
1.Throwable
是异常的基类,分为Error和Exception,在编程中我们关注Exception。
2.Exception
分为编译期异常(受检)和运行期异常(非受检)。
3.注意:
1.异常会导致程序中断,无法继续执行。
2.在开发中我们需要可能的出现的异常的代码,使用try语句块包起来。
3.处理异常可以让程序保持运行状态
4.catch可以有多个,顺序为从子类到父类。如果父类在前,后面的子类不可能被执行到
4.代码 事例:
int[] a = {1,2,3,4,5};
//try代码快中有可能出现的异常都可以在catch中捕获
try {
a = null;
System.out.println(a.length);
int y =a[4];
int x = 3/1;
System.out.println(x);
} catch (ArithmeticException e) { //数学算术异常
System.err.println("除数不能为零!");
}catch (ArrayIndexOutOfBoundsException e) { //数组下标越界
System.err.println("数组下标越界!");
}catch (NullPointerException e) { //空指针异常
System.err.println("空指针异常!");
}
5.异常处理过程分析:
1.程序一旦产生异常,则系统会自动产生一个异常类的实例化对象。
2.此时如果存在了try语句,则会自动找到匹配的catch语句执行,如果没有异常处理,则程序将会退出,由系统报告错误。
3.所有的catch根据方法的参数,匹配异常类的实例化对象,如果匹配成功,则由此catch进行处理
6.finally关键字:
1.在异常处理之后,在异常的处理格式中还有一个finally语句,那么此语句将作为异常的统一出口。不管是否异常,都要执行这段代码。
2.try中有renturn语句,如果有finally语句,则finally语句块在try中的return之前执行。
面试题:final不可变的,finally异常处理,finallylize垃圾回收
7.throw与throws关键字:
例:
public class ExceptionDemo1 {
public static void main(String[] args) {
methon(10, 0);
}
public static int methon(int a,int b)throws ArithmeticException {
try {
int c = a/b;
return c;
} catch (ArithmeticException e) {
throw new ArithmeticException("除数不能为零!");
}finally {
System.err.println("运行结束...");
}
}
}
异常:
运行结束...
Exception in thread "main" java.lang.ArithmeticException: 除数不能为零!
at com.lemon.ExceptionDemo1.methon(ExceptionDemo1.java:16)
at com.lemon.ExceptionDemo1.main(ExceptionDemo1.java:8)
throw与throws常常在一起使用
8.异常处理的语法规则:
1.try语句不能单独存在,可以和catch组成try...catch...finally、try...catch、try...finally三种结构,catch语句可以有一个或者多个,finally语句最多只能有一个,try、catch、finally语句均不能单独使用。
2.try、catch、finally代码块中变量的作用域分别独立而不能相互访问。
3.多个catch块时,Java虚拟机会匹配其中一个异常类或其子类,就执行此catch块,而不会再执行其他catch块。
9.自定义异常:
1.定义自己的异常类MyException
/**
* 自定义异常通常都是通过继承一个异常类
*1、Throwable
*2、Exception
*3、RuntimeException
* 自定义异常通常的实现是:提供构造方法
* 异常对象本身没有什么实际功能,只是一个有意义的标识
*
* @author lemonSun
*
* 2019年4月12日下午8:56:45
*/
public class MyException extends Exception{
public MyException() {
super();
}
public MyException(String message) {
super(message);
}
}
2.服务类(用于登录验证):(只有用户:admin,密码:123456才能通过)
public class UserService {
public User login(String username,String password)throws MyException {
if(!"admin".equals(username)) {
throw new MyException("用户名错误!");
}
if(!"123456".equals(password)) {
throw new MyException("密码错误!");
}
User user = new User("admin","123456",10,"男");
return user;
}
}
3.User用户实体类:
public class User {
private String userName;
private String password;
private int age;
private String sex;
public User() {
super();
}
public User(String userName, String password, int age, String sex) {
super();
this.userName = userName;
this.password = password;
this.age = age;
this.sex = sex;
}
public String getUserName() {
return userName;
}
public void setUserName(String userName) {
this.userName = userName;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
@Override
public String toString() {
return "User [userName=" + userName + ", password=" + password + ", age=" + age + ", sex=" + sex + "]";
}
}
4.主程序 登录:
import java.util.Scanner;
public class LoginDemo {
public static void main(String[] args){
Scanner scanner = new Scanner(System.in);
System.out.println("请输入用户名:");
String username = scanner.nextLine();
System.out.println("请输入密码:");
String password = scanner.nextLine();
UserService userService = new UserService();
try {
User user = userService.login(username, password);
System.out.println("登录成功!");
System.out.println(user);
} catch (MyException e) {
e.printStackTrace();
}
}
}
测试:
请输入用户名:
asd
请输入密码:
ad
com.lemon.MyException: 用户名错误!
at com.lemon.UserService.login(UserService.java:8)
at com.lemon.LoginDemo.main(LoginDemo.java:17)
10.受检(Exception)和非受检异常(RunTimeException):
Exception:受检异常,在编译期检查,在调用抛出这个异常的方法时,必须显示的使用try...catch...
RunTimeException:非受检异常,在运行期检查,在调用抛出这个异常的方法时,可以不用显示的使用try...catch...
注意:在使用自定义异常时,根据实际的业务需求,来决定哪个作为父类。
11.assert(断言)
public class AssertDemo {
public static void main(String[] args) {
int c =add(3,3);
assert c == 7:"结果不正确!";
}
public static int add(int a,int b) {
return a + b;
}
}
配置下JVM:
Run -> Run configuration ->
结果:
try 1.7之后新特性:
//1.7新特新
//自动关闭流
try(BufferedReader buf = new BufferedReader(new InputStreamReader(System.in))) {
String info = buf.readLine();
//buf.close(); //try自动帮助关闭
System.out.println(info);
} catch (IOException e) {
e.printStackTrace();
}