异常的介绍及应用详解(Java)

异常

1.异常介绍

1.概述:代码出现了不正常的现象;在java中,异常都是一个一个的类                

在这里插入图片描述

public class Demo01Exception {
    public static void main(String[] args) throws ParseException {
        //错误Error -> StackOverflowError
        //method();

        //运行时期异常 -> ArrayIndexOutOfBoundsException
        int[] arr1 = new int[3];
        //System.out.println(arr1[4]);
        
        /*
          编译时期异常:
           注意看:编译时期异常是我们代码写错了嘛?不是,当我们调用方法的时候
           该方法底层给我们抛了一个编译时期异常,所以导致我们一调用此方法
           一编译,就爆红了
           当我们一旦触发了这个异常,jvm就会将异常信息打印到控制台上,给程序员们看
         */
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        String time = "2000-10-10 10:10:10";
        Date date = sdf.parse(time);
        System.out.println(date);
    }

    public static void method(){
        method();
    }
}

2.异常出现的过程

3.创建异常对象(了解)

创建异常对象,只是为了后面学习如何处理异常,其他的暂时没有啥意义

1.关键字:throw
2.格式: throw new 异常
public class Demo03Exception {
    public static void main(String[] args) {
        String s = "a.tx1t";
        method(s);
    }
    public static void method(String s){
        if (!s.endsWith(".txt")){
            //故意创建异常对象,用throw说明此处有异常
            throw new NullPointerException();
        }
        System.out.println("我要执行了");
    }
}

4.异常处理方式(重点)

4.1 异常处理方式一_throws

1.格式:在方法参数和方法体之间位置上写
  throws 异常
2.意义:处理异常
  将异常往上抛
public class Demo04Exception {
    public static void main(String[] args)throws FileNotFoundException {
        String s = "a.txt1";
        add(s);//添加功能
        delete();//删除功能
        update();//修改功能
        find();//查询功能
    }


    private static void add(String s)throws FileNotFoundException {
        if (!s.endsWith(".txt")) {
            //故意创建异常
            throw new FileNotFoundException("文件找不到");
        }
        System.out.println("我要执行了");
    }

    private static void find() {
        System.out.println("查询功能");
    }

    private static void update() {
        System.out.println("修改功能");
    }

    private static void delete() {
        System.out.println("删除功能");
    }
}

4.2 异常处理方式一_throws多个异常

1.格式:throws 异常1,异常2
    
2.注意:
  如果throws的多个异常之间有子父类继承关系,我们可以直接throws父类异常
  如果不知道多个异常之间是否有子父类继承关系,我们可以直接throws Exception    
public class Demo05Exception {
    public static void main(String[] args)throws /*FileNotFoundException,*//*IOException*/Exception {
        String s = null;
        add(s);//添加功能
        delete();//删除功能
        update();//修改功能
        find();//查询功能
    }


    private static void add(String s)throws /*FileNotFoundException,*//*IOException*/Exception {
        if (s==null){
            //故意造异常
            throw new IOException("IO异常");
        }
        if (!s.endsWith(".txt")) {
            //故意创建异常
            throw new FileNotFoundException("文件找不到");
        }
        System.out.println("我要执行了");
    }

    private static void find() {
        System.out.println("查询功能");
    }

    private static void update() {
        System.out.println("修改功能");
    }

    private static void delete() {
        System.out.println("删除功能");
    }

}

4.3 异常处理方式二_try…catch

1.格式:
  try{
      可能出现异常的代码
  }catch(异常 对象名){
      处理异常的代码-> 将来开发会将异常信息保存到日志文件中
  }
public class Demo06Exception {
    public static void main(String[] args){
        String s = "a.txt1";
        try{
            //int[] arr = null;
            //System.out.println(arr.length);//NullPointerException
            add(s);//添加功能
        }catch (FileNotFoundException e){
            System.out.println(e);
        }

        delete();//删除功能
        update();//修改功能
        find();//查询功能
    }


    private static void add(String s)throws FileNotFoundException {
        if (!s.endsWith(".txt")) {
            //故意创建异常
            throw new FileNotFoundException("文件找不到");
        }
        System.out.println("我要执行了");
    }

    private static void find() {
        System.out.println("查询功能");
    }

    private static void update() {
        System.out.println("修改功能");
    }

    private static void delete() {
        System.out.println("删除功能");
    }

}

4.4.异常处理方式二_多个catch

1.格式:
  try{
      可能出现异常的代码
  }catch(异常 对象名){
      处理异常的代码-> 将来开发会将异常信息保存到日志文件中
  }catch(异常 对象名){
      处理异常的代码-> 将来开发会将异常信息保存到日志文件中
  }catch(异常 对象名){
      处理异常的代码-> 将来开发会将异常信息保存到日志文件中
  }catch(异常 对象名){
      处理异常的代码-> 将来开发会将异常信息保存到日志文件中
  }...
      
2.注意:
  如果catch的多个异常之间有子父类继承关系,我们可以直接catch父类异常
  如果不知道多个异常之间是否有子父类继承关系,我们也可以直接catch Exception    
public class Demo07Exception {
    public static void main(String[] args) {
        String s = null;
       /* try {
            add(s);//添加功能
        }catch (FileNotFoundException e){
            System.out.println(e);
        }catch (IOException e){
            System.out.println(e);
        }*/

        /*try {
            add(s);//添加功能
        }catch (IOException e){
            System.out.println(e);
        }*/

        try {
            add(s);//添加功能
        }catch (Exception e){
            e.printStackTrace();//将详细的异常信息打印到控制台上
        }
        delete();//删除功能
        update();//修改功能
        find();//查询功能
    }


    private static void add(String s) throws FileNotFoundException, IOException {
        if (s == null) {
            //故意造异常
            throw new IOException("IO异常");
        }
        if (!s.endsWith(".txt")) {
            //故意创建异常
            throw new FileNotFoundException("文件找不到");
        }
        System.out.println("我要执行了");
    }

    private static void find() {
        System.out.println("查询功能");
    }

    private static void update() {
        System.out.println("修改功能");
    }

    private static void delete() {
        System.out.println("删除功能");
    }

}

5.finally关键字

1.概述:代表的是不管是否触发了异常,都会执行的代码块
  特殊情况:如果之前执行了System.exit(0)终止当前正在执行的java虚拟机
2.使用:都是配合try...catch使用
  try{
      可能出现异常的代码
  }catch(异常 对象名){
      处理异常的代码-> 将来开发会将异常信息保存到日志文件中
  }finally{
      不管是否有异常,都会执行的代码
  }  
public class Demo08Exception {
    public static void main(String[] args){
        String s = "a.txt";
        try {
            add(s);//添加功能
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }finally {
            System.out.println("我必须滴执行");
        }
    }


    private static void add(String s)throws FileNotFoundException {
        if (!s.endsWith(".txt")) {
            //故意创建异常
            throw new FileNotFoundException("文件找不到");
        }
        System.out.println("我要执行了");
    }
}

public class Demo09Exception {
    public static void main(String[] args) {
        int result = method();
        System.out.println(result);
    }

    public static int method() {
        try {
            String s = null;
            System.out.println(s.length());//空指针异常
            return 2;
        } catch (Exception e) {
            return 1;
        } finally {
            System.out.println("我一定要执行");
            //return 3;
        }
    }
}

finally的使用场景:

1.关闭资源

2.原因:对象如果没有用了,GC(垃圾回收器)回收,用来回收堆内存中的垃圾,释放内存,但是有一些对象GC回收不了,比如:连接对象(Connection),IO流对象,Socket对象,这些对象GC回收不了,就需要我们自己手动回收,手动关闭

​ 将来不能回收的对象new完之后,后续操作不管是否操作成功,是否有异常,我们都需要手动关闭,此时我们就可以将关闭资源的代码放到finally中

public class Test {
 public static void main(String[] args) {
     FileWriter fw = null;
     try {
         fw = new FileWriter("day13_exception_object\\1.txt");
         fw.write("哈哈哈");//假如这里写失败或者写成功了
     } catch (IOException e) {
         throw new RuntimeException(e);
     }finally {
         if (fw!=null){
             try {
                 fw.close();
             } catch (IOException e) {
                 throw new RuntimeException(e);
             }
         }

     }
 }
}

6.抛异常时注意的事项

1.如果父类中的方法抛了异常,那么子类重写之后要不要抛?
  可抛可不抛  
2.如果父类中的方法没有抛异常,那么子类重写之后要不要抛?  
  不要抛  
public class Demo10Exception {
    public static void main(String[] args) {

    }
    class A{
        public void method()/*throws Exception*/{

        }
    }

    class B extends A{
        @Override
        public void method()/*throws Exception*/{

        }
    }
}

7.try_catch和throws的使用时机

1.如果处理异常之后,还想让后续的代码正常执行,我们使用try...catch
2.如果方法之间是递进关系(调用),我们可以先throws,但是到了最后需要用try...catch做一个统一的异常处理

1.编译时期异常是必须要处理的,不处理爆红,没法往下写

a.throws

b.try…catch

2.运行时期异常我们一般不处理,一旦出现运行时期异常,肯定是代码写的有问题,我们直接修改代码细节就行啦

8.自定义异常

1.需求:键盘录入一个用户名,实现登录功能,如果登录失败,抛出LoginUserException
public class LoginUserException extends Exception{
    public LoginUserException() {
    }

    public LoginUserException(String message) {
        super(message);
    }
}

public class Demo11Exception {
    public static void main(String[] args) throws LoginUserException {
        //1.定义一个用户名,代表已经注册的用户
        String username = "root";
        //2.创建Scanner对象,录入用户名
        Scanner sc = new Scanner(System.in);
        System.out.println("请您输入要登录的用户名:");
        String name = sc.next();
        //3.判断用户名是否和已经存在的用户名一致
        if (name.equals(username)){
            System.out.println("登录成功了");
        }else{
            throw new LoginUserException("登录失败了,用户名或者密码有问题");
        }
    }
}

1.定义一个类

2.如果继承Exception 就是编译时期异常

3.如果继承RuntimeException,就是运行时期异常

9.打印异常信息的三个方法

Throwable类中的方法:
  String toString()  :输出异常类型和设置的异常信息
  String getMessage(): 输出设置的异常信息  
  void printStackTrace():打印异常信息是最全的:包括异常类型,信息,以及出现的行数等      
public class Demo11Exception {
    public static void main(String[] args) {
        //1.定义一个用户名,代表已经注册的用户
        String username = "root";
        //2.创建Scanner对象,录入用户名
        Scanner sc = new Scanner(System.in);
        System.out.println("请您输入要登录的用户名:");
        String name = sc.next();
        //3.判断用户名是否和已经存在的用户名一致
        if (name.equals(username)) {
            System.out.println("登录成功了");
        } else {
            try {
                throw new LoginUserException("登录失败了,用户名或者密码有问题");
            }catch (Exception e){
                //System.out.println(e.toString());
                //System.out.println(e.getMessage());
                e.printStackTrace();
            }
        }
    }
}
  • 7
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值