/**
从大体来分异常为两块:
1、error---错误 : 是指程序无法处理的错误,表示应用程序运行时出现的重大错误。
2、Exception --- 异常 :异常可分为 运行时异常 和 编译异常
(1)运行时异常:即RuntimeException及其之类的异常。
这类异常在代码编写的时候 不会被编译器所检测出来,是可以不需要被捕获, 但是程序员也可以根据需要进行捕获抛出。
常见的RUNtimeException有: NullpointException(空指针异常)
ClassCastException(类型转换异常)
IndexOutOfBoundsException(数组越界异常)
ArithmeticException(算术异常)例除数位零
IllegalArgumentException(不合法参数异常)
NumberFormatException(数字转换格式异常)
IndexOutOfBoundsException(下标越界异常)
(2)编译异常:RuntimeException以外的异常。这类异常在编译时 编译器会提示 需要捕获,如果不进行捕获则编译错误。
常见编译异常有:IOException(流传输异常),SQLException(数据库操作异常)
throw与throws的异同
1.throws出现在方法函数头;而throw出现在函数体。
2.throws表示出现异常的一种可能性,并不一定会发生这些异常;throw则是抛出了异常,若执行throw了则一定抛出了某种异常对象。
3、两者都是消极处理异常的方式,只是抛出或可能抛出异常,但是不会由函数去处理异常,真正的处理异常由函数的上层调用处理
*/
import java.util.Scanner;
/**
捕获异常
try{
产生异常的代码
}catch(){
处理异常
}catch(子异常){
catch块可以有多个,分别用于处理不同的异常类型
}
...
catch(异常基类 Exception e){
}finally{
无论是否异常都会执行
}
不能先捕获父类再捕获子类
*/
public class Demo1 {
// 异常捕获................................................
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
System.out.println("请输入第一个数:");
int num1 = scanner.nextInt();
System.out.println("请输入第二个数:");
int num2 = scanner.nextInt();
try {// 程序可能出现的问题,
// 如果没有问题,就执行try块里面的代码,catch块里的代码不会执行,最后执行finally块代码
// 如果有问题,try块里面的代码不执行,程序会往下走,执行catch块里的代码,最后执行finally块代码
double result = num1 / num2;
System.out.println(num1 + "/" + num2 + "=" + result);
} catch (ArithmeticException e) {
// catch{这个块里的代码,是用来处理代码出现问题后要做的事} 比如打印代码出错的原因
// catch(这个是 Exception 类,或子类 异常实例)
System.out.println("除数不能为零!");
} finally {
// finally块是可选项,不管try块中是否产生异常,都会执行finally块的代码
System.out.println("Finally 已经执行,程序结束");
}
}
}
/*..........................
请输入第一个数:
10
请输入第二个数:
2
10/2=5.0
Finally 已经执行,程序结束
............................
请输入第一个数:
10
请输入第二个数:
0
除数不能为零!
Finally 已经执行,程序结束
* */
public class Demo2 {
//运行时异常 声明 ,可抛可不抛
public static void main(String[] args) {
int num1=10;
int num2=0;
try {
System.out.println(divide(num1,num2));//捕获
}catch(ArithmeticException e) {
System.out.println("除数能为0 ");//处理
}
}
//throws 在方法的参数后面,用来声明该方法的异常列表
//throws是,方法可能抛出异常的声明。(用在声明方法时,表示该方法可能要抛出异常)
//当某个方法可能会抛出某种异常时,用throws 声明可能抛出的异常,然后交给上层调用它的方法程序处理
private static double divide(int num1, int num2) throws ArithmeticException{//.....................
return num1/num2;
}
}
//运行得:除数能为0
/**
*
* 抛出异常 throws 异常对象 例如:throw new ArithmeticException();
*/
public class Demo3 {
// 运行时异常 声明 ,可抛可不抛
public static void main(String[] args) {
int num1 = 10;
int num2 = 0;
try {
System.out.println(divide(num1, num2));// 两数相除
} catch (ArithmeticException e) {
System.out.println("产生异常:" + e.getMessage());// 处理:获取异常信息
}
}
// throw,是语句抛出一个异常,一般是在代码块的内部,当程序出现某种逻辑错误时由程序员主动抛出某种特定类型的异常
private static double divide(int num1, int num2) {
if (num2 == 0) {
throw new ArithmeticException("除数不能为0 ");//.................................
} else {
return num1 / num2;
}
}
}
//运行得:产生异常:除数不能为0
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
public class Demo4 {
//编译异常:RuntimeException以外的异常。
//这类异常在编译时 编译器会提示 需要捕获,如果不进行捕获则编译错误
public static void main(String[] args) {
System.out.println("请输入数字:");
int num;
BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
try {
num=Integer.parseInt(br.readLine());//必须捕获
System.out.println("输出:"+num);
} catch (NumberFormatException e) {
System.out.println("数字格式异常");
} catch (IOException e) {
e.printStackTrace();
}
}
}
/*
运行得:
请输入数字:
123
输出:123
请输入数字:
asdas
数字格式异常
* */
//自定义异常
public class Demo5 {
public static void main(String[] args) {
//手机号登陆
String[] phones= {"15688886666","15688885555","15688884444"};
String phone="1568888";
try {
int index=login(phones,phone);
if(phone.length()!=11) {
throw new InvalidPhoneException("手机号码长度不合法!");//这个就是抛出的自己定义的一个异常..........
}else if(index==-1) {
System.out.println("手机号码不正确!");
}else {
System.out.println("登陆成功!");
}
}catch(InvalidPhoneException e) {
System.out.println("有异常:"+e.getMessage());//返回错误解释信息
//e.printStackTrace();//输出堆栈信息
}
}
//运行时异常,方法体后,可抛可不抛,最好抛,让调用者知道这个方法可能会出现异常
public static int login(String[] phones, String phone)throws InvalidPhoneException {
for (int i = 0; i < phones.length; i++) {
if(phones[i].equals(phone)) {
return i;
}
}
return -1;
}
}
/**
运行:
有异常:手机号码长度不合法!
*/
/**
自定义异常
如果写一个编译时异常类,则需要继承 Exception 类。
如果写一个运行时异常类,那么需要继承 RuntimeException 类。
名称:一定要见名之意
自定义异常作用:明确错误的原因
怎么写:先继承,里面都是调用两个构造函数就行了 ,用来报错的
*/
//自定义一个 无效的手机号异常,
//这个是运行的时候检验是否是11位数字,若不是11位,会报告异常,打印消息,需要继承RuntimeException
public class InvalidPhoneException extends RuntimeException{
public InvalidPhoneException() {
super();
// TODO Auto-generated constructor stub
}
public InvalidPhoneException(String arg0) {
super(arg0);
// TODO Auto-generated constructor stub
}
}