===== 异常结构 ===== {{:pasted:20160301-214457.png}} ===== 异常种类 ===== * Error:程序无法处理的异常(如:OutOfMemoryError) * Exception:程序可以处理的异常。还分两种 * 运行时异常:不需要显示处理也能编译,但最终需要被捕获(如:NullPointerException) * 检查异常:需要显示处理或抛出异常,否则编译不通过(如:IOException) * java认为Checked异常都是可以被处理(修复)的异常,所以必须强制处理 ===== 异常抛出 ===== * 导致当前流程无法正常继续执行的错误,或者,程序可以处理的错误 -> 抛出RunTimeException * 空指针 * 除数为0等等 * 程序无法处理的错误 -> 抛出Error * 内存溢出 * 导致程序永远无法正常工作错误 -> 抛出Error * 关键数据库ip配置错误 ===== 异常处理 ===== * 如果知道异常如何处理,则捕获并且处理 * 如果自己不能修复,则继续抛出 * 遇到检查异常,可以转换成运行时异常 try { FileInputStream in=new FileInputStream("/a.txt"); } catch (FileNotFoundException e) { throw new RuntimeException("file exception"); } * 程序最外层统一处理异常 * 如果程序种使用了assert,那异常捕获的时候要注意assert的异常类型(Error类型) try { main(); // 不一定是main函数,这里只最上层的函数 } catch (RuntimeException e){ // 所有运行时异常在这里统一处理 System.out.println("handle RuntimeException error here"); } catch (Error e){ // 如果是junit异常,捕获并处理 if(e.getClass().toString().contains("junit")) { System.out.println("handle junit error here"); } else { // 如果不是junit异常,则一定是系统级异常,程序已经无法处理,抛出异常,终止程序 System.out.println("handle error here"); throw e; } } ===== 自定义异常 ===== 异常是一个比较耗时的操作,异常性能差是因为fillInStackTrace方法,该方法是带锁的并且需要填充线程异常栈信息。 而我们的业务类异常是不需要记录异常栈的,可以考虑覆写fillInStackTrace方法减小性能开支(据说覆写该方法能提高10倍性能)。 class BizException extends Exception{ public BizException(String message) { super(message); } public Throwable fillInStackTrace() { return this; } }