1、在框架层面粗狂的捕获和处理异常不可取的。
2、finally代码块中的异常需要注意,避免覆盖原始异常。如下例子,无论是否异常,都需要最后释放BufferedReader 资源,但是收尾操作同样可能出现异常。可能finally中的异常会将try中的异常覆盖。有以下几个方法处理该问题
①在finally代码中自己捕获处理
②使用addSuppressed将异常全部抛出
③使用try-with-resources来释放资源
//例1
public static List<String> read(String fileName) throws IOException {
BufferedReader bufferedReader = null;
try {
FileSystem fs = FileSystem.get(URI.create(PATH), conf);
FSDataInputStream fsr = fs.open(new Path(""));
bufferedReader = new BufferedReader(new InputStreamReader(fsr));
//...
} finally {
if (bufferedReader != null) {
try {
bufferedReader.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
return null;
}
//例2
public static List<String> read(String fileName) throws IOException {
Exception ex = null;
BufferedReader bufferedReader = null;
try {
FileSystem fs = FileSystem.get(URI.create(PATH), conf);
FSDataInputStream fsr = fs.open(new Path(""));
bufferedReader = new BufferedReader(new InputStreamReader(fsr));
//...
} catch (Exception e) {
ex = e;
} finally {
if (bufferedReader != null) {
try {
bufferedReader.close();
} catch (IOException e) {
if (e!= null) {
ex.addSuppressed(e);
} else {
ex = e;
}
}
}
}
return null;
}
//例3
public static List<String> read(String fileName) throws IOException {
try (FileSystem fs = FileSystem.get(URI.create(PATH), conf);
FSDataInputStream fsr = fs.open(new Path(""));
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(fsr));) {
//...
} catch (Exception e) {
System.out.println(e);
}
//...
}
3、捕获异常后就一定要进行处理,不能直接生吞,反例如下:
public void wrong() {
try {
...
} catch (Exception e) {//原始异常
throw new RuntimeException("系统异常");
}
}
4、不能将异常定义为静态变量,避免异常栈信息错乱
public class Main {
public static void main(String[] args) {
try {
wrong();
} catch (Exception ex) {
System.out.println("createOrder got error" + ex);
}
try {
wrong2();
} catch (Exception ex) {
System.out.println("createlOrder got error" + ex);
}
}
private static void wrong() {
throw Exceptions.EXISTS;
}
private static void wrong2() {
throw Exceptions.EXISTS;
}
}
上述代码wrong2打出的异常堆栈信息提示显示了wrong方法,出现了异常信息固化。所以异常栈一定要根据当前调用来动态获取。