Java异常处理

一、Java中的异常处理

        java中的异常处理类中的最顶级类是java.lang.Throwable类

        Throwable产生了两个直接子类,分别是Error【错误】/Exception【异常】

二、Error【错误】与 Exception【异常】的区别?

        Exception【异常】:程序正常运行中可以预料的意外情况,可能并且应该被捕获,进行相应处理。

        Error【错误】:指在正常情况下不大可能出现的情况,绝大部分的Error都会导致程序(比如JVM自身)处于非正常的、不可恢复状态。既然是非正常情况,所以不便于也不需要捕获,常见的比如OutOfMemoryError之类,都是Error的子类。

三、Exception【异常】分类

        1.检查性异常:在源代码里必须显式地进行捕获处理

        2.非检查性异常:就是所谓的运行时异常,通常是可以编码避免的逻辑错误,具体根据需要来判断是否需要捕获,并不会在编译期强制要求捕获处理。

        处理非检查性异常[运行时异常]的步骤
                1.查找出现异常的位置【看控制台输出的错误信息】
                2.确定具体的异常类型
                3.编码避免

        如何查找出现异常的位置和确定具体的异常类型?如何才能输出异常提示信息?

                通过try{}catch(具体异常对象){}将异常提示信息输出。具体异常对象.printStackTrace();---打印堆栈异常

四、Java异常处理的原理

        1.try…catch捕获处理异常---将异常提示信息输出
            格式:
                    try{
                        可能出现异常的java代码
                    }catch(异常对象){
                        异常对象---处理异常    
                    }
        当程序没有异常的时候,那么程序正常运行不会进入try…catch中;
        当程序出现异常的时候,try块就会将出现的具体异常捕获,程序将不会继续向下执行,转而执行catch块,并将try块捕获的异常封装成一个异常对象交给catch块,由catch块处理异常,处理完成以后就接着继续向下执行。

public class TestMain2 {
	public static void main(String[] args) {
		try {
			int a = 10;
			int b = 0;
			int c = a / b;
			System.out.println("c==" + c);
		} catch (ArithmeticException e) {
			e.printStackTrace();
		}
	}
}

注意:i.将可能出现异常的java代码用try{}块包围。
           ii.catch后面的异常对象应该是一个具体的异常对象。
        我们目前所见到的异常有限,我们可能不能知道这个异常的具体名称,这时我们可以使用Exception或者Throwable对象代替。

public class TestMain2 {
	public static void main(String[] args) {
		try {
			int a = 10;
			int b = 0;
			int c = a / b;
			System.out.println("c==" + c);
		} catch (Exception e) {
			e.printStackTrace();
		}
	}
}

public class TestMain2 {
	public static void main(String[] args) {
		try {
			int a = 10;
			int b = 0;
			int c = a / b;
			System.out.println("c==" + c);
		} catch (Throwable e) {
			e.printStackTrace();
		}
	}
}

          iii.一个try{}块后面可以有多个catch块,多个catch块要按照异常类型由小到大排列

public class TestMain2 {
	public static void main(String[] args) {
		try {
			int a = 10;
			int b = 0;
			int c = a / b;
			System.out.println("c==" + c);
		}catch (ArithmeticException e) {
			System.out.println("出异常");
			e.printStackTrace();
		}catch (Exception e) {
			System.out.println("出异常");
			e.printStackTrace();
		}catch (Throwable e) {
			System.out.println("出异常");
			e.printStackTrace();
		}
	}
}

          iv. finally{}块出现在最后一个catch块后面,无论程序是否发生异常都会执行。

public class TestMain2 {
	public static void main(String[] args) {
		try {
			int a = 10;
			int b = 0;
			int c = a / b;
			System.out.println("c==" + c);
		}catch (ArithmeticException e1) {
			System.out.println("假装出里异常");
			e1.printStackTrace();
		}catch (Exception e2) {
			System.out.println("假装出里异常");
			e2.printStackTrace();
		}catch (Throwable e3) {
			System.out.println("假装出里异常");
			e3.printStackTrace();
		}finally{
			System.out.println("无论程序是否发生异常都会执行");
		}
	}
}

        由于异常Exception本身是程序正常运行中可以预料的意外情况,我们通过修改程序可以避免这个异常的发生,所以我们在try{}catch(Exception e){}的catch块中不进行具体异常的处理,而是通过异常对象的printStackTrace()方法将异常类型和异常原因以及出现异常的位置找到,然后修改程序来避免这个异常的发生。

        2.不断向上抛出,交由jvm来处理
            throws--声明方法抛出异常
            访问限制修饰符  返回值类型  方法名称([参数])throws 异常类型{}
            访问限制修饰符  返回值类型  方法名称([参数])throws 异常类型1,异常类型2...{}
            throws--声明方法抛出异常,结果是在那里调用这个方法你就要处理方法上的异常

public class Person {
	//throws--声明方法抛出异常
	//访问限制修饰符  返回值类型  方法名称([参数])throws 异常类型{}
	public  void  testPerson()throws Exception{
		int num=10/0;
		System.out.println("num=="+num);
	}
}

package com.wangxing.test3;
public class TestMain3 {
	public static void main(String[] args) {
		Person p1=new Person();
		try{
		p1.testPerson();
		}catch(Exception e){
			e.printStackTrace();
		}
	}
}





public class Person {
	//throws--声明方法抛出异常
	//访问限制修饰符  返回值类型  方法名称([参数])throws 异常类型{}
	public  void  testPerson()throws Exception{
		int num=10/0;
		System.out.println("num=="+num);
	}
}

package com.wangxing.test3;
public class TestMain3 {
	public static void main(String[] args)throws Exception {
		Person p2=new Person();
		p2.testPerson();
		
	}
}




/*
结果:
Exception in thread "main" java.lang.ArithmeticException: / by zero
	at com.wangxing.test3.Person.testPerson(Person.java:7)
	at com.wangxing.test3.TestMain3.main(TestMain3.java:15)
*/

五、throw关键字的用法

        throw关键字表示手动产生一个异常【故意制造异常】。
            目的:为了提醒用户怎么操作。
            格式:throw new 异常类名称([提示语言]);

        自定义异常:java开发库中没有提供,我们自己创建的异常。很多时候java发库中提供异常类型是满足我们的开发使用的,很少自定义异常。

        怎么做一个自定义异常的简单的方法:
              1.创建一个新类,继承一下Exception/Throwable
              2.重新构建一下子类的构造方法,通过super([参数])调用父类的构造方法。

//创建一个新类,并继承Exception类,重构子类构造函数,用super调用父类的构造方法
public class MyException extends Exception{
	public MyException(String msg){
		super(msg);
	}
}


/*
  创建数组的java类
 */
public class MyArray {
	//数组大小
	private int size;
	//通过构造方法设置数组大小
	public MyArray(int size)throws MyException{
		if(size<=0){
			//手动产生一个异常,提示提醒用户不用使用负数
			throw new MyException("数组大小不能是负数!");
		}else{
			this.size=size;
		}
	}
	//创建一个字符串类型的数组
	public  String[]  createArray(){
		String  stringarray[]=new String[this.size];
		return stringarray;
	}
}


public class TestMain4 {
	public  static  void  main(String args[])throws Exception{
		MyArray  myarray1=new MyArray(-1);
		String name[]=myarray1.createArray();
	}
}

/*
Exception in thread "main" com.wangxing.test4.MyException: 数组大小不能是负数!
	at com.wangxing.test4.MyArray.(MyArray.java:14)
	at com.wangxing.test4.TestMain4.main(TestMain4.java:4)
*/

你可能感兴趣的:(java,开发语言)