hi,你好!欢迎访问本站!登录
本站由网站地图腾讯云宝塔系统阿里云强势驱动
当前位置:首页 - 教程 - 杂谈 - 正文 君子好学,自强不息!

【java基本之非常】死了都要try,不极尽描摹地catch我不愉快!

2019-11-18杂谈搜奇网36°c
A+ A-

目次

  • 1、非常
    • 1.1 非常观点
    • 1.2 非常系统
    • 1.3 非常分类
    • 1.4 非常的发作历程剖析
  • 2、 非常的处置惩罚
    • 2.1 抛出非常throw
    • 2.2 Objects非空推断
    • 2.3 声明非常throws
    • 2.4 捕捉非常try…catch
    • 2.4 finally 代码块
    • 2.5 finally 代码块与return语句
    • 2.6 非常注重事项
  • 3、自定义非常
    • 3.1 概述
    • 3.2 自定义非常演习
    • 4、来!和非常大干一场

@

1、非常

1.1 非常观点

非常 :简朴说就是不正常运转,终究致使JVM的非正常住手。

在Java等面向对象的编程语言中,非常本身是一个类,发作非常就是建立非常对象并抛出了一个非常对象。Java处置惩罚非常的体式格局是中断处置惩罚。

非常指的并非语法毛病,语法错了,编译不经由过程,不会发作字节码文件,基本不能运转.

1.2 非常系统

非常机制现实上是协助我们找到顺序中的题目,非常的根类是java.lang.Throwable,其下有两个子类:java.lang.Errorjava.lang.Exception,寻常所说的非常指java.lang.Exception

Throwable中的经常运用要领:

1、 public void printStackTrace():打印非常的详细信息。

包含了非常的范例,非常的缘由,还包含非常涌现的位置,在开辟和调试阶段,都得运用printStackTrace。

2、 public String getMessage():猎取发作非常的缘由。

提示给用户的时刻,就提示毛病缘由。

3、 public String toString():猎取非常的范例和非常形貌信息(不必)。

涌现非常,最简朴的体式格局就是把非常的简朴类名,拷贝到API中去查。

1.3 非常分类

我们寻常说的非常就是指Exception,由于这类非常一旦涌现,我们就要对代码举行改正,修复顺序。

非常(Exception)的分类:依据在编译时代照样运转时代去搜检非常?

  • 编译时代非常:checked非常。在编译时代,就会搜检,假如没有处置惩罚非常,则编译失利。(如日期花样化非常)
  • 运转时代非常:runtime非常。在运转时代,搜检非常.在编译时代,运转非常不会编译器检测(不报错)。(如数学非常)

1.4 非常的发作历程剖析

先运转下面的顺序,顺序会发作一个数组索引越界非常ArrayIndexOfBoundsException。我们经由过程图解来剖析下非常发作的历程。

东西类

public class ArrayTools {
    // 对给定的数组经由过程给定的角标猎取元素。
    public static int getElement(int[] arr, int index) {
        int element = arr[index];
        return element;
    }
}

测试类

public class ExceptionDemo {
    public static void main(String[] args) {
        int[] arr = { 34, 12, 67 };
        intnum = ArrayTools.getElement(arr, 4)
        System.out.println("num=" + num);
        System.out.println("over");
    }
}

上述顺序实行历程图解:

2、 非常的处置惩罚

Java非常处置惩罚的五个关键字:trycatchfinallythrowthrows

2.1 抛出非常throw

在编写顺序时,作为一个优异的顺序员必需要斟酌顺序涌现题目的状况。举个栗子,在定义要领时,要领须要接收参数。那末,当挪用要领运用接收到的参数时,起首须要先对参数数据举行正当的推断,数据若不正当,就应该通知挪用者,通报正当的数据进来。这时候须要运用抛出非常的体式格局来通知挪用者。这个时刻throw就派上用场了!

在java中,供应了一个throw关键字,Throw用来抛出一个指定的非常对象。从而可以

1、建立一个非常对象。封装一些提示信息(信息可以本身编写)。

2、经由过程关键字throw就可以将这个非常对象示知给挪用者,还可以将这个非常对象通报到挪用者处。

throw小结

throw用在要领内,背面接一个非常对象,运用花样为throw new 非常类名(参数);,将这个非常对象通报到挪用者处,并完毕当前要领的实行。

throw运用的花样以下
~~~java
throw new NullPointerException("要接见的arr数组不存在");

throw new ArrayIndexOutOfBoundsException("该索引在数组中不存在,已超出范围");
~~~

运用throw的实例运用

public class ThrowDemo {
    public static void main(String[] args) {
        //建立一个数组 
        int[] arr = {2,4,52,2};
        //依据索引找对应的元素 
        int index = 4;
        int element = getElement(arr, index);

        System.out.println(element);
        System.out.println("over");
    }
    /*
     * 依据 索引找到数组中对应的元素
     */
    public static int getElement(int[] arr,int index){ 
        //推断  索引是不是越界
        if(index<0 || index>arr.length-1){
             /*
             推断前提假如满足,当实行完throw抛出非常对象后,要领已没法继续运算。
             这时候就会完毕当前要领的实行,并将非常示知给挪用者。这时候就须要经由过程非常来处理。 
              */
             throw new ArrayIndexOutOfBoundsException("哥们,角标越界了~~~");
        }
        int element = arr[index];
        return element;
    }
}

throw运转效果剖析:

再来看看不运用throw的实例运用的运转

  public static void main(String[] args) {
        //建立一个数组
        int[] arr = {2,4,52,2};
        //依据索引找对应的元素
        int index = 4; //注重索引4已越界了
        int ele=arr[index];

        System.out.println(ele);
        System.out.println("over");
}

运转效果

如许一对照throw的上风就显而易见了~

2.2 Objects非空推断

还记得Objects类吗,曾提到过它由一些静态的有用要领构成,这些要领是null-save(空指针平安的)或null-tolerant(容忍空指针的),那末在它的源码中,对对象为null的值举行了抛出非常操纵。

public static <T> T requireNonNull(T obj):检察指定援用对象不是null。

检察源码发明这里对为null的举行了抛出非常操纵:

public static <T> T requireNonNull(T obj) {
    if (obj == null)
        throw new NullPointerException();
    return obj;
}

2.3 声明非常throws

假如发作了题目,我们就会throw将题目形貌类即非常举行抛出,也就是将题目返回给该要领的挪用者。

那末关于挪用者来讲,该如何处置惩罚呢?一种是举行捕捉处置惩罚,另一种就是继续讲题目声明出去,运用throws声明处置惩罚。

声明非常:将题目标识出来,报告给挪用者。假如要领内经由过程throw抛出了编译时非常,而没有捕捉处置惩罚(稍后解说该体式格局),那末必需经由过程throws举行声明,让挪用者去处置惩罚。

throws小结

关键字throws运用于要领声明之上,throws花样为修饰符 返回值范例 要领名(参数) throws 非常类名1,非常类名2…{ },用于示意当前要领不处置惩罚非常,而是提示该要领的挪用者来处置惩罚非常(抛出非常).

声明非常的代码演示:

public class ThrowsDemo {
    public static void main(String[] args) throws FileNotFoundException {
        read("a.txt");
    }

    // 假如定义功用时有题目发作须要报告给挪用者。可以经由过程在要领上运用throws关键字举行声明
    public static void read(String path) throws FileNotFoundException {
        if (!path.equals("a.txt")) {//假如不是 a.txt这个文件 
            // 我假定  假如不是 a.txt 以为 该文件不存在 是一个毛病 也就是非常  throw
            throw new FileNotFoundException("文件不存在");
        }
    }
}

throws用于举行非常类的声明,若该要领可以有多种非常状况发作,那末在throws背面可以写多个非常类,用逗号离隔。

public class ThrowsDemo2 {
    public static void main(String[] args) throws IOException {
        read("a.txt");
    }

    public static void read(String path)throws FileNotFoundException, IOException {
        if (!path.equals("a.txt")) {//假如不是 a.txt这个文件 
            // 我假定  假如不是 a.txt 以为 该文件不存在 是一个毛病 也就是非常  throw
            throw new FileNotFoundException("文件不存在");
        }
        if (!path.equals("b.txt")) {
            throw new IOException();
        }
    }
}

throw 和 throws 的区分小结

throw:

1、示意要领内抛出某种非常对象
2、假如非常对象是非 RuntimeException 则须要在要领申明时加上该非常的抛出 即须要加上 throws 语句 或许 在要领体内 try catch 处置惩罚该非常,不然编译报错
3、实行到 throw 语句则背面的语句块不再实行

throws:

1、要领的定义上运用 throws 示意这个要领可以抛出某种非常
2、须要由要领的挪用者举行非常处置惩罚

2.4 捕捉非常try…catch

假如非常涌现的话,会马上停止顺序,所以我们得处置惩罚非常:

  1. 该要领不处置惩罚,而是声明抛出,由该要领的挪用者来处置惩罚(throws)。
  2. 在要领中运用try-catch的语句块来处置惩罚非常。

try-catch的体式格局就是捕捉非常。

捕捉非常:Java中对非常有针对性的语句举行捕捉,可以对涌现的非常举行指定体式格局的处置惩罚。

捕捉非常语法以下:

try{
     编写可以会涌现非常的代码
}catch(非常范例  e){
     处置惩罚非常的代码
     //纪录日记/打印非常信息/继续抛出非常
}

try:该代码块中编写可以发作非常的代码。

catch:用来举行某种非常的捕捉,完成对捕捉到的非常举行处置惩罚。

注重:trycatch都不能零丁运用,必需连用。

演示以下:

public class TryCatchDemo {
    public static void main(String[] args) {
        try {// 当发作非常时,必需有处置惩罚体式格局。要么捕捉,要么声明。
            read("b.txt");
        } catch (FileNotFoundException e) {// 括号中须要定义什么呢?
            //try中抛出的是什么非常,在括号中就定义什么非常范例
            System.out.println(e);
        }
        System.out.println("over");
    }
    /*
     *
     * 我们 当前的这个要领中 有非常  有编译期非常
     */
    public static void read(String path) throws FileNotFoundException {
        if (!path.equals("a.txt")) {//假如不是 a.txt这个文件 
            // 我假定  假如不是 a.txt 以为 该文件不存在 是一个毛病 也就是非常  throw
            throw new FileNotFoundException("文件不存在");
        }
    }
}

如何猎取非常信息:

Throwable类中定义了一些检察要领:

1、 public String getMessage():猎取非常的形貌信息,缘由(提示给用户的时刻,就提示毛病缘由。

2、 public String toString():猎取非常的范例和非常形貌信息(不必)。

3、 public void printStackTrace():打印非常的跟踪栈信息并输出到控制台。

包含了非常的范例,非常的缘由,还包含非常涌现的位置,在开辟和调试阶段,都得运用printStackTrace。

2.4 finally 代码块

finally:有一些特定的代码不论非常是不是发作,都须要实行。别的,由于非常会激发顺序跳转,致使有些语句实行不到。而finally就是处理这个题目的,在finally代码块中寄存的代码都是肯定会被实行的。

什么时刻的代码必需终究实行?

当我们在try语句块中翻开了一些物理资本(磁盘文件/网络衔接/数据库衔接等),我们都得在运用完以后,终究封闭翻开的资本。

finally的语法:

try...catch....finally:本身须要处置惩罚非常,终究还得封闭资本。

注重:finally不能零丁运用。

比如在IO流中,当翻开了一个关联文件的资本,末了顺序不论效果如何,都须要把这个资本封闭掉。

finally代码参考以下:

public class TryCatchDemo4 {
    public static void main(String[] args) {
        try {
            read("a.txt");
        } catch (FileNotFoundException e) {
            //抓取到的是编译期非常  抛出去的是运转期 
            throw new RuntimeException(e);
        } finally {
            System.out.println("不论顺序如何,这里都将会被实行。");
        }
        System.out.println("over");
    }
    /*
     *
     * 我们 当前的这个要领中 有非常  有编译期非常
     */
    public static void read(String path) throws FileNotFoundException {
        if (!path.equals("a.txt")) {//假如不是 a.txt这个文件 
            // 我假定  假如不是 a.txt 以为 该文件不存在 是一个毛病 也就是非常  throw
            throw new FileNotFoundException("文件不存在");
        }
    }
}

当只要在try或许catch中挪用退出JVM的相干要领,此时finally才不会实行,不然finally永久会实行。

2.5 finally 代码块与return语句

另有个迥殊主要的点就是在try块或catch块中碰到return语句时,finally语句块将在要领返回之前被实行,别的finally语句中也可以有return语句,然则只管防止有return语句(会报正告)

2.6 非常注重事项

多个非常运用捕捉又该如何处置惩罚呢?

  1. 多个非常离别处置惩罚。

  2. 多个非常一次捕捉,屡次处置惩罚。
  3. 多个非常一次捕捉一次处置惩罚。

平常我们是运用一次捕捉屡次处置惩罚体式格局,花样以下:

try{
     编写可以会涌现非常的代码
}catch(非常范例A  e){  当try中涌现A范例非常,就用该catch来捕捉.
     处置惩罚非常的代码
     //纪录日记/打印非常信息/继续抛出非常
}catch(非常范例B  e){  当try中涌现B范例非常,就用该catch来捕捉.
     处置惩罚非常的代码
     //纪录日记/打印非常信息/继续抛出非常
}

注重:这类非常处置惩罚体式格局,请求多个catch中的非常不能雷同,而且若catch中的多个非常之间有子父类非常的关联,那末子类非常请求在上面的catch处置惩罚,父类非常鄙人面的catch处置惩罚。

非常注重小结

  • 运转时非常被抛出可以不处置惩罚。即不捕捉也不声明抛出。

  • 假如finallyreturn语句,永久返回finally中的效果,防止该状况. 上面也提到过!

  • 假如父类抛出了多个非常,子类重写父类要领时,抛出和父类雷同的非常或许是父类非常的子类或许不抛出非常。

  • 父类要领没有抛出非常,子类重写父类该要领时也不可抛出非常。此时子类发作该非常,只能捕捉处置惩罚,不能声明抛出

3、自定义非常

3.1 概述

为何须要自定义非常类:

Java中差别的非常类,离别示意着某一种详细的非常状况,在开辟中老是有些非常状况是SUN没有定义好的,此时我们依据本身营业的非常状况来定义非常类。比方顺序员头发数为负数、小明考试成绩负数题目等等。

在之前顺序代码中,发明这些非常都是JDK内部定义好的,然则现实开辟中也会涌现许多非常,这些非常很可以在JDK中没有定义过,比方顺序员妻子数目为负数、顺序员老王智商为负数题目.那末能不能本身定义非常呢?答案是能滴!

什么是自定义非常类:

在开辟中依据本身营业的非常状况来定义非常类.

自定义一个营业逻辑非常: RegisterException。一个注册非常类。

非常类如何定义:

  1. 自定义一个编译期非常: 自定义类 并继续于java.lang.Exception
  2. 自定义一个运转时代的非常类:自定义类 并继续于java.lang.RuntimeException

3.2 自定义非常演习

比如说我们模仿注册操纵,假如用户名已存在,则抛出非常并提示:亲,该用户名已被注册。

起首定义一个上岸非常类RegisterException

// 营业逻辑非常
public class RegisterException extends Exception {
    /**
     * 空参组织
     */
    public RegisterException() {
    }

    /**
     *
     * @param message 示意非常提示
     */
    public RegisterException(String message) {
        super(message);
    }
}

模仿上岸操纵,运用数组模仿数据库中存储的数据,并供应当前注册账号是不是存在要领用于推断。

public class Demo {
    // 模仿数据库中已存在账号
    private static String[] names = {"bill","hill","jill"};
   
    public static void main(String[] args) {     
        //挪用要领
        try{
              // 可以涌现非常的代码
            checkUsername("nill");
            System.out.println("注册胜利");//假如没有非常就是注册胜利
        }catch(RegisterException e){
            //处置惩罚非常
            e.printStackTrace();
        }
    }

    //推断当前注册账号是不是存在
    //由因而编译期非常,又想挪用者去处置惩罚 所以声明该非常
    public static boolean checkUsername(String uname) throws RegisterException {
        for (String name : names) {
            if(name.equals(uname)){//假如名字在这内里 就抛出上岸非常
                throw new RegisterException("亲"+name+"已被注册了!");
            }
        }
        return true;
    }
}

用户名不存在,登录胜利,效果剖析以下:

用户名存在,登录失利,效果剖析以下:

4、来!和非常大干一场

本篇文章到这里基本就看完了,博主我也不知道列位吸收了若干,我得对列位们担任鸭,不能讲完就完事了,因而照样以为让列位稳固稳固一下比较好,假如列位可以做出下面这道典范的非常题,申明非常方面的学问对你来讲就没多大题目了,假如以为那里还不是迥殊懂,可以实时通知我,通常看到了都邑第一时间复兴。好了,试想一下下面顺序运转效果是啥~

package com.gx.Expetion;

public class TestException {
    public TestException() {
    }
    boolean testEx() throws Exception {
        boolean ret = true;
        try {
            ret = testEx1();
        } catch (Exception e) {
            System.out.println("testEx, catch exception");
            ret = false;
            throw e;
        } finally {
            System.out.println("testEx, finally; return value=" + ret);
            return ret;
        }
    }
 
    boolean testEx1() throws Exception {
        boolean ret = true;
        try {
            ret = testEx2();
            if (!ret) {
                return false;
            }
            System.out.println("testEx1111, at the end of try");
            return ret;
        } catch (Exception e) {
            System.out.println("testEx1111, catch exception");
            ret = false;
            throw e;
        } finally {
            System.out.println("testEx1111, finally; return value=" + ret);
            return ret;
        }
    }
 
    boolean testEx2() throws Exception {
        boolean ret = true;
        try {
            int b = 12;
            int c;
            for (int i = 2; i >= -2; i--) {
                c = b / i;
                System.out.println("i=" + i);
            }
            return true;
        } catch (Exception e) {
            System.out.println("testEx2222, catch exception");
            ret = false;
            throw e;
        } finally {
            System.out.println("testEx2222, finally; return value=" + ret);
            return ret;
        }
    }
 
    public static void main(String[] args) {
        TestException testException1 = new TestException();
        try {
            testException1.testEx();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

运转效果:

i=2
i=1
testEx2222, catch exception
testEx2222, finally; return value=false
testEx1111, finally; return value=false
testEx, finally; return value=false

假如以为那里还不是迥殊懂,可以实时通知我,通常看到了都邑第一时间复兴!!!

到这里,许多小白同砚照旧木有感遭到博主“死了都要try,不极尽描摹地catch我不愉快!”的谁人feel,对咩?行,博主就满足满足小白的谁人feel,feelfeel一下 ~=感觉感觉一下~

 /**
     * 把多条数据的ResultSet的效果放到 List<T>中
     * @param rs  ResultSet效果集
     * @param obj java类的class
     * @return
     */
    public static <T> List<T> getResult(ResultSet rs, Class<T> obj) {
        try {
            List<T> list = new ArrayList<T>();
            //ResultSetMetaData 有关 ResultSet 中列的称号和范例的信息。
            ResultSetMetaData metaData = rs.getMetaData();
            //猎取总的列数
            int count = metaData.getColumnCount();
            //遍历ResultSet
            while (rs.next()) {
                //---建立对象实例
                T instance = obj.newInstance();
                for (int i = 1; i <= count; i++) {
                    //---猎取列名
                    String name = metaData.getColumnName(i);
                    // 转变列名花样成 java 定名花样 主如果针对 _ 支解的状况  如user_id
                    name = toJavaField(name);
                    //---猎取范例
                    Class<?> type = obj.getDeclaredField(name).getType();
                    //---猎取setter要领
                    // 首字母大写
                    String replace = name.substring(0, 1).toUpperCase() + name.substring(1);
                    Method setMethod = obj.getMethod("set" + replace, type);

                    //---推断读取数据的范例
                    if (type.isAssignableFrom(String.class)) {
                        setMethod.invoke(instance, rs.getString(i));
                    } else if (type.isAssignableFrom(int.class) || type.isAssignableFrom(Integer.class)) {
                        setMethod.invoke(instance, rs.getInt(i));
                    } else if (type.isAssignableFrom(Boolean.class) || type.isAssignableFrom(boolean.class)) {
                        setMethod.invoke(instance, rs.getBoolean(i));
                    } else if (type.isAssignableFrom(Date.class)) {
                        setMethod.invoke(instance, rs.getDate(i));
                    }
                }
                list.add(instance);
            }
            return list;

        } catch (SQLException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (InstantiationException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (NoSuchFieldException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (SecurityException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (NoSuchMethodException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IllegalArgumentException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (InvocationTargetException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (Exception e) {
            // TODO: handle exception
        }

        return null;
    }

先不说看不看得懂了,以上代码设想反射、泛型、非常~也就是try..catch~ 、String类、jdbc相干的学问,这些学问我大部分都写过文章了,有兴致的小白同砚就直接点蓝色字体进入文章。咳咳...言归正传,有木有发明以上代码中运用的就是一次捕捉屡次处置惩罚体式格局,花样以下:

try{
     编写可以会涌现非常的代码
}catch(非常范例A  e){  当try中涌现A范例非常,就用该catch来捕捉.
     处置惩罚非常的代码
     //纪录日记/打印非常信息/继续抛出非常
}catch(非常范例B  e){  当try中涌现B范例非常,就用该catch来捕捉.
     处置惩罚非常的代码
     //纪录日记/打印非常信息/继续抛出非常
}

注重:这类非常处置惩罚体式格局,请求多个catch中的非常不能雷同,而且若catch中的多个非常之间有子父类非常的关联,那末子类非常请求在上面的catch处置惩罚,父类非常鄙人面的catch处置惩罚。

这已是第二次写到了,所以列位找到不极尽描摹地catch不愉快的feel了咩?

末了,引荐阅读本专栏的下两篇java文章~有兴致的同砚可以相识一下~

【java基本之多态】明白多态的向上向下转型从“妈妈我想吃烤山药”讲起

【java基本】java继续从“我爸是李刚”讲起

迎接列位关注我的民众号,一同讨论手艺,憧憬手艺,寻求手艺...

  选择打赏方式
微信赞助

打赏

QQ钱包

打赏

支付宝赞助

打赏

  移步手机端
【java基本之非常】死了都要try,不极尽描摹地catch我不愉快!

1、打开你手机的二维码扫描APP
2、扫描左则的二维码
3、点击扫描获得的网址
4、可以在手机端阅读此文章
未定义标签

本文来源:搜奇网

本文地址:https://www.sou7.cn/282291.html

关注我们:微信搜索“搜奇网”添加我为好友

版权声明: 本文仅代表作者个人观点,与本站无关。其原创性以及文中陈述文字和内容未经本站证实,对本文以及其中全部或者部分内容、文字的真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。请记住本站网址https://www.sou7.cn/搜奇网。

发表评论

选填

必填

必填

选填

请拖动滑块解锁
>>