栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

Java 异常

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

Java 异常

文章目录
  • 异常定义
    • 步骤 1 : try catch
    • 步骤 2 : 使用异常的父类进行catch
    • 步骤 3 : 多异常捕捉办法1
    • 步骤 4 : 多异常捕捉办法2
    • 步骤 5 : finally
    • 步骤 6 : throws
    • 步骤 7 : throw和throws的区别
    • 最佳实践1
    • 最佳实践2
    • 最佳实践3
  • 异常分类
    • 步骤1 : 可查异常
    • 步骤2:运行时异常
    • 步骤3:错误
  • Throwable
  • 自定义异常

异常定义

异常处理常见手段: try catch finally throws throw

步骤 1 : try catch

1、将可能抛出ArrayIndexOutOfBoundsException数组角标越界异常的代码放在try里

2、如果角标存在,就会顺序往下执行,并且不执行catch块中的代码

3、如果角标不存在,try 里的代码会立即终止,程序流程会运行到对应的catch块中

4、e.printStackTrace(); 会打印出方法的调用痕迹,这样就便于定位和分析到底哪里出了异常

		try {
			int[] arrays= {1,2,3,4,5}; //【0】-【4】
			int n=5;
			//预感数组角标可能会有问题
			System.out.println(arrays[n]);//java.lang.ArrayIndexOutOfBoundsException: 5  数组角标超出最大值
			//出现问题的时候后面的代码无法执行
			System.out.println("hello");
		} catch (ArrayIndexOutOfBoundsException e) {
			System.out.println("肯定是角标异常了哟,检查一下");
			//代码执行轨迹
			e.printStackTrace();
		}

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-1aqY3LDm-1653905117038)(%E5%BC%82%E5%B8%B8.assets/clip_image002.jpg)]

步骤 2 : 使用异常的父类进行catch

ArrayIndexOutOfBoundsException是Exception的子类,使用Exception也可以catch住ArrayIndexOutOfBoundsException

		try {
			int[] arrays= {1,2,3,4,5}; //【0】-【4】
			int n=5;
			//预感数组角标可能会有问题
			System.out.println(arrays[n]);//java.lang.ArrayIndexOutOfBoundsException: 5  数组角标超出最大值
			//出现问题的时候后面的代码无法执行
			System.out.println("hello");
		} catch (Exception e) {
			System.out.println("肯定是角标异常了哟,检查一下");
			//代码执行轨迹
			e.printStackTrace();
		}

步骤 3 : 多异常捕捉办法1

需求,出现了算术异常,又可能出现数组下标越界,我们希望出现哪个就打印哪个的问题,这里需要多异常捕获

		try {
			int a=1/1;//java.lang.ArithmeticException: / by zero  零不能当除数
			System.out.println(a);
		
			int[] arrays= {1,2,3,4,5}; //【0】-【4】
			int n=5;
			//预感数组角标可能会有问题
			System.out.println(arrays[n]);//java.lang.ArrayIndexOutOfBoundsException: 5  数组角标超出最大值
			//出现问题的时候后面的代码无法执行
			System.out.println("hello");
			//连续捕获
		} catch(ArithmeticException e1) {
			
			System.out.println("除数不可以为0");
			e1.printStackTrace();//打印一下代码运行轨迹
			
		}catch (ArrayIndexOutOfBoundsException e2) {//向上转型  Exception e=new java.lang.ArrayIndexOutOfBoundsException();
			System.out.println("肯定是角标异常了哟,检查一下");
			//代码执行轨迹
			e2.printStackTrace();
		}

步骤 4 : 多异常捕捉办法2

Jdk7之后出现了一种新的连续捕获方法,方便的是可以一次捕获完,不方便的是需要多次处理

		try {
			int a=1/1;//java.lang.ArithmeticException: / by zero  零不能当除数
			System.out.println(a);
		
			int[] arrays= {1,2,3,4,5}; //【0】-【4】
			int n=5;
			//预感数组角标可能会有问题
			System.out.println(arrays[n]);//java.lang.ArrayIndexOutOfBoundsException: 5  数组角标超出最大值
			//出现问题的时候后面的代码无法执行
			System.out.println("hello");
			//连续捕获
		} catch(ArithmeticException | ArrayIndexOutOfBoundsException e) {//向上转型  Exception e=new java.lang.ArrayIndexOutOfBoundsException();
			if(e instanceof ArithmeticException) {
				System.out.println("除数不能为零");
			}else if(e instanceof ArrayIndexOutOfBoundsException) {
				System.out.println("肯定是角标异常了哟,检查一下");
			}
			//代码执行轨迹
			e.printStackTrace();
		}

步骤 5 : finally

无论是否出现异常,finally中的代码都会被执行

finally {//最终执行

​ System.out.println(“出问题了哈?该背时”);

}

步骤 6 : throws

考虑如下情况:
主方法调用method1
method1调用method2
method2中访问数组,可能会越界

method2中需要进行异常处理
但是method2不打算处理,而是把这个异常通过throws抛出去
那么method1就会接到该异常。 处理办法也是两种,要么是try catch处理掉,要么也是抛出去。
method1选择本地try catch住 一旦try catch住了,就相当于把这个异常消化掉了,主方法在调用method1的时候,就不需要进行异常处理了

public class Demo28 {

	public static void main(String[] args) {
		method1();
	}
	public static void method1() {
//		method2(4);
		//method1针对method3有可能会出现的ArrayIndexOutOfBoundsException的问题,使用try-catch语句预防一下
		try {
			method3(4);
		}catch(ArrayIndexOutOfBoundsException e) {
			System.out.println("啊啊啊啊啊啊-角标越界");
			e.printStackTrace();
			method3(2);
		}
	}
	//throws 抛出
	//不想自己解决,一旦出现问题,让调用者自己来解决
	//throws声明异常(问题),意味着:有可能会出现问题,但不一定会出现问题,一旦出现问题,抛给调用者去解决
	public static void method3(int n)throws ArrayIndexOutOfBoundsException {
		int[] a= {1,2,6};//0 1 [2]
		System.out.println(a[n]);
	}
	
	//当一段代码出现问题,两种思路解决,第一种就地解决
	public static void method2(int n) {
		try {
			int[] a= {1,2,6};
			System.out.println(a[n]);
		} catch (ArrayIndexOutOfBoundsException e) {
			System.out.println("角标越界");
			method2(2);
		}
	}
	
}

步骤 7 : throw和throws的区别

throws与throw这两个关键字接近,不过意义不一样,有如下区别:

  1. throws 出现在方法声明上,而throw通常都出现在方法体内。

  2. throws 表示出现异常的一种可能性,并不一定会发生这些异常;throw则是抛出了异常,执行throw则一定抛出了某个异常对象。

最佳实践1
public class Demo28 {

	public static void main(String[] args) {
		try {
			method1();
		} catch (Exception e) {
			method3(2);
		}
	}
	public static void method1()throws ArrayIndexOutOfBoundsException {
//		method2(4);
		//method1针对method3有可能会出现的ArrayIndexOutOfBoundsException的问题,使用try-catch语句预防一下
		try {
			method3(4);
		}catch(ArrayIndexOutOfBoundsException e) {
			System.out.println("啊啊啊啊啊啊-角标越界");
			e.printStackTrace();
			//这里做一个基本处理后交给下一个处理
			throw new ArrayIndexOutOfBoundsException("数组角标越界"); 
		}
	}
	//throws 抛出
	//不想自己解决,一旦出现问题,让调用者自己来解决
	//throws声明异常(问题),意味着:有可能会出现问题,但不一定会出现问题,一旦出现问题,抛给调用者去解决
	public static void method3(int n)throws ArrayIndexOutOfBoundsException {
		int[] a= {1,2,6};//0 1 [2]
		System.out.println(a[n]);
	}
	
	//当一段代码出现问题,两种思路解决,第一种就地解决
	public static void method2(int n) {
		try {
			int[] a= {1,2,6};
			System.out.println(a[n]);
		} catch (ArrayIndexOutOfBoundsException e) {
			System.out.println("角标越界");
			method2(2);
		}
	}
	
}


最佳实践2
package com.haoyu;

public class Demo29 {

	public static void main(String[] args) {
		//开心到死
		thirdHappyEnding();
	}
	//3,养老院
	public static void thirdHappyEnding() {
		try {
			secondRescue();
		} catch (Exception e) {
			System.out.println("房已开好,等你哟");
		}
	}
	
	//2,做手术
	public static void secondRescue()throws HappyLifeException{
		//看一下包扎之后需不需要做手术,如果接收到一个做手术的问题,就开始做手术
		try {
			firstRescue();
		} catch (OperateException e) {
			System.out.println("手术已经做完");
			throw new HappyLifeException("可以养老了");
		}
	}
	
	//1,战场基本消毒和包扎
	public static void firstRescue()throws OperateException {
		//打仗过程有可能会出问题,临时抢救一下
		try {
			ware();
		}catch(ChangziZhaChuanException e) {
			System.out.println("包扎和消毒");
			//挂号做手术--跟手术相关的问题
			throw new OperateException("修复手术可以做了哟");
		}
	}
	//打仗,打仗过程一不小心肠子被炸穿,向上抛出一个被炸穿的异常(问题)(求救信号)
	//打仗之前就必须建立起医疗的通讯机制
	public static void ware() throws ChangziZhaChuanException{
		throw new ChangziZhaChuanException("炸得连渣都不剩");
	}
	
}
//需求:打仗
//负伤
//1,战场基本消毒和包扎
//2,运输回后方,医生做手术
//3,送回养老院,孤独终老
//我们自定义一个异常,继承了运行时出问题的异常类,描述上述问题
//肠子被炸穿异常
class ChangziZhaChuanException extends RuntimeException{
	private String name;
	public ChangziZhaChuanException(String name) {
		super(name);
		this.name = name;
	}
} 
//做手术的问题--挂号
class OperateException extends RuntimeException{
	private String name;
	public OperateException(String name) {
		super(name);
		this.name = name;
	}
} 
//送往养老院,开开心心地去死
class HappyLifeException extends RuntimeException{
	private String name;
	public HappyLifeException(String name) {
		super(name);
		this.name = name;
	}
}

最佳实践3

参照exception包中的电脑案例 如何把异常都处理完?

异常分类

异常分类: 可查异常,运行时异常和错误3种。
其中,运行时异常和错误又叫非可查异常。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Z1MX10oP-1653905117039)(%E5%BC%82%E5%B8%B8.assets/clip_image004.jpg)]

步骤1 : 可查异常

可查异常: CheckedException
可查异常即必须进行处理的异常,要么try catch住,要么往外抛,谁调用,谁处理,比如 FileNotFoundException如果不处理,编译器,就不让你通过。

步骤2:运行时异常

运行时异常RuntimeException指: 不是必须进行try catch的异常
常见运行时异常***
除数不能为0异常:ArithmeticException
下标越界异常:ArrayIndexOutOfBoundsException
空指针异常:NullPointerException
在编写代码的时候,依然可以使用try catch throws进行处理,与可查异常不同之处在于,即便不进行try catch,也不会有编译错误
Java之所以会设计运行时异常的原因之一,是因为下标越界,空指针这些运行时异常太过于普遍,如果都需要进行捕捉,代码的可读性就会变得很糟糕。

步骤3:错误

错误Error,指的是系统级别的异常,通常是内存用光了
在默认设置下,一般java程序启动的时候,最大可以使用16m的内存
如例不停的给StringBuffer追加字符,很快就把内存使用光了。抛出OutOfMemoryError
与运行时异常一样,错误也是不要求强制捕捉的

Throwable

Throwable是类,Exception和Error都继承了该类
所以在捕捉的时候,也可以使用Throwable进行捕捉
如图: 异常分Error和Exception
Exception里又分运行时异常和可查异常

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-1iKbKp9n-1653905117039)(%E5%BC%82%E5%B8%B8.assets/clip_image006.jpg)]

import java.io.File;
import java.io.FileInputStream;
 
public class TestException {
 
    public static void main(String[] args) {
 
        File f = new File("d:/LOL.exe");
 
        try {
            new FileInputStream(f);
            //使用Throwable进行异常捕捉
        } catch (Throwable t) {
            // TODO Auto-generated catch block
            t.printStackTrace();
        }
 
    }
}
自定义异常

实现 throwable 或者继承运行时异常类

try语句在返回前,将其他所有的操作执行完,保留好要返回的值,而后转入执行finally中的语句,而后分为以下三种情况:

情况一:如果finally中有return语句,则会将try中的return语句”覆盖“掉,直接执行finally中的return语句,得到返回值,这样便无法得到try之前保留好的返回值。

情况二:如果finally中没有return语句,也没有改变要返回值,则执行完finally中的语句后,会接着执行try中的return语句,返回之前保留的值。

情况三:如果finally中没有return语句,但是改变了要返回的值,这里有点类似与引用传递和值传递的区别,分以下两种情况:

1)如果return的数据是基本数据类型或文本字符串,则在finally中对该基本数据的改变不起作用,try中的return语句依然会返回进入finally块之前保留的值。

2)如果return的数据是引用数据类型,而在finally中对该引用数据类型的属性值的改变起作用,try中的return语句返回的就是在finally中改变后的该属性的值。

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/936804.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号