Java中的异常处理不是一个简单的主题。初学者发现很难理解,甚至有经验的开发人员也可以花几个小时讨论如何以及应该抛出或处理哪些异常。

这就是为什么大多数开发团队都有自己的如何使用它们的规则。如果你是一个团队的新手,你可能会惊讶于这些规则与你之前使用过的规则有多么不同。

尽管如此,大多数团队都使用了几种最佳实践。以下是帮助您入门或改进异常处理的9个最重要的内容。

1.清理finally块中的资源或使用Try-With-Resource语句

经常发生在try块中使用资源,比如InputStream,之后需要关闭它。这些情况中的一个常见错误是在try块结束时关闭资源。

public  void  doNotCloseResourceInTry(){FileInputStream  inputStream  =  null ;尝试 {文件 文件 =  新 文件(“./tmp.txt”);inputStream  =  new  FileInputStream(file);//使用inputStream读取文件// 不要这样做inputStream。close();} catch(FileNotFoundException  e){记录。错误(e);} catch(IOException  e){记录。错误(e);}}

问题是只要没有抛出异常,这种方法似乎完全正常。try块中的所有语句都将被执行,资源将被关闭。

但是你添加了try块是有原因的。您调用一个或多个可能抛出异常的方法,或者您自己抛出异常。这意味着您可能无法到达try块的末尾。因此,您不会关闭资源。

因此,您应该将所有清理代码放入finally块或使用try-with-resource语句。

使用Finally块

与try块的最后几行相比,finally块始终执行。这可以在成功执行try块之后或在catch块中处理异常之后发生。因此,您可以确保清理所有已打开的资源。

public void closeResourceInFinally(){
FileInputStream inputStream = null ;
尝试 {
文件 文件 = 新 文件(“./tmp.txt”);
inputStream = new FileInputStream(file);
//使用inputStream读取文件
} catch(FileNotFoundException e){
记录。错误(e);
} finally {
if(inputStream != null){
尝试 {
inputStream。close();
} catch(IOException e){
记录。错误(e);
}
}
}
}

Java 7的资源尝试声明

另一种选择是try-with-resource语句,我在Java异常处理的介绍中对此进行了更详细的解释。

如果资源实现AutoCloseable接口,则可以使用它。这就是大多数Java标准资源所做的事情。当您在try子句中打开资源时,它将在try块执行后自动关闭,或者处理异常。

public void automaticCloseResource(){
文件 文件 = 新 文件(“./tmp.txt”);
try(FileInputStream inputStream = new FileInputStream(file);){
//使用inputStream读取文件
} catch(FileNotFoundException e){
记录。错误(e);
} catch(IOException e){
记录。错误(e);
}
}

2.偏好特定例外情况

抛出的异常越具体越好。请记住,不知道您的代码的同事,或者您可能在几个月内需要调用您的方法并处理异常。

因此,请务必提供尽可能多的信息。这使您的API更易于理解。因此,您的方法的调用者将能够更好地处理异常或通过额外的检查来避免它。

因此,总是尝试找到最适合您的异常事件的类,例如抛出NumberFormatException而不是IllegalArgumentException。并避免抛出非特定的异常

public void doNotDoThis()抛出 异常 {
...
}
public void doThis()抛出 NumberFormatException {
...
}

3.记录您指定的例外情况

无论何时在方法签名中指定异常,都应该在Javadoc中记录它。这与以前的最佳实践具有相同的目标:为调用者提供尽可能多的信息,以便他可以避免或处理异常。

因此,请确保向Javadoc 添加@throws声明并描述可能导致异常的情况。

/ **
*这种方法非常有用......
*
* @param输入
* @throws MyBusinessException如果......发生
* /
public void doSomething(String input)throws MyBusinessException {
...
}

4.使用描述性消息抛出异常

这种最佳实践背后的想法类似于前两种实践。但是这次,您不向调用方提供有关方法的信息。每个必须了解在日志文件或监视工具中报告异常时发生的事情的人都会读取异常的消息。

因此,它应该尽可能准确地描述问题,并提供最相关的信息来理解异常事件。

别误会我的意思; 你不应该写一段文字。但是你应该用1-2个简短的句子来解释这个例外的原因。这有助于您的运营团队了解问题的严重性,还可以让您更轻松地分析任何服务事件。

如果抛出一个特定的异常,它的类名很可能已经描述了那种错误。因此,您无需提供大量其他信息。一个很好的例子是NumberFormatException。当您以错误的格式提供String时,它会被类java.lang.Long的构造函数抛出。

尝试 {
新 龙(“xyz”);
} catch(NumberFormatException e){
记录。错误(e);
}

NumberFormatException类的名称已经告诉您问题的类型。它的消息只需要提供导致问题的输入字符串。如果异常类的名称不具有表现力,则需要在消息中提供所需的信息。

17:17:26,386错误TestExceptionHandling:52 - java.lang.NumberFormatException:对于输入字符串:“xyz”

5.首先捕获最具体的例外

大多数IDE都可以帮助您实现这一最佳实践。当您尝试首先捕获不太具体的异常时,它们会报告无法访问的代码块。

问题是只有匹配异常的第一个catch块才会被执行。因此,如果首先捕获IllegalArgumentException,则永远不会到达应该处理更具体的NumberFormatException的catch块,因为它是IllegalArgumentException的子类。

始终首先捕获最具体的异常类,并将不太具体的catch块添加到列表的末尾。

您可以在以下代码段中看到此类try-catch语句的示例。第一catch块处理所有NumberFormatException的S和第二个所有抛出:IllegalArgumentException S的不是NumberFormatException异常

public void catchMostSpecificExceptionFirst(){
尝试 {
doSomething(“消息”);
} catch(NumberFormatException e){
记录。错误(e);
} catch(IllegalArgumentException e){
记录。错误(e)
}
}

6.不要抓住可扔的

Throwable是所有异常和错误的超类。你可以在catch子句中使用它,但你永远不应该这样做!

如果在catch子句中使用Throwable,它不仅会捕获所有异常; 它还会捕获所有错误。JVM抛出错误以指示应用程序无意处理的严重问题。典型的例子是OutOfMemoryErrorStackOverflowError。两者都是由应用程序无法控制的情况引起的,无法处理。

所以,最好不要抓住Throwable,除非你完全确定你处于一个特殊情况,你可以或者需要处理错误。

public void doNotCatchThrowable(){
尝试 {
// 做一点事
} catch(Throwable t){
//不要这样做!
}
}

7.不要忽视例外

您是否曾经分析过只有用例的第一部分被执行的错误报告?

这通常是由忽略的异常引起的。开发人员可能非常确定它永远不会被抛出并添加了一个不处理或记录它的catch块。当你发现这个区块时,你很可能甚至会发现一个着名的“这将永远不会发生”的评论。

public void doNotIgnoreExceptions(){
尝试 {
// 做一点事
} catch(NumberFormatException e){
//这永远不会发生
}
}

好吧,你可能正在分析一个不可能发生的问题。

所以,请永远不要忽视异常。您不知道代码将来会如何变化。有人可能会删除阻止异常事件的验证而不会认识到这会产生问题。或者抛出异常的代码会被更改,现在抛出同一个类的多个异常,并且调用代码不会阻止所有这些异常。

你至少应该写一条日志消息,告诉大家不可思议的事情刚刚发生,而且有人需要检查它。

public void logAnException(){
尝试 {
// 做一点事
} catch(NumberFormatException e){
记录。错误(“这不应该发生:” + e);
}
}

8.不要记录和投掷

这可能是此列表中最常被忽略的最佳做法。您可以找到许多代码片段,甚至是可以捕获,记录和重新抛出异常的库。

尝试 {
新 龙(“xyz”);
} catch(NumberFormatException e){
记录。错误(e);
扔 é ;
}

在发生异常时记录异常可能会感觉很直接,然后重新抛出它以便调用者可以适当地处理它。但它会为同一个异常写出多条错误消息。

17:44:28,945 ERROR TestExceptionHandling:65 - java.lang.NumberFormatException:对于输入字符串:“xyz”
线程“main”中的异常java.lang.NumberFormatException:对于输入字符串:“xyz”
at java.lang.NumberFormatException.forInputString(NumberFormatException.java:65)
在java.lang.Long.parseLong(Long.java:589)
在java.lang.Long。(Long.java:965)
at com.stackify.example.TestExceptionHandling.logAndThrowException(TestExceptionHandling.java:63)
at com.stackify.example.TestExceptionHandling.main(TestExceptionHandling.java:58)

其他消息也不添加任何信息。如最佳实践#4中所述,异常消息应描述异常事件。堆栈跟踪告诉您抛出异常的类,方法和行。

如果需要添加其他信息,则应捕获异常并将其包装在自定义异常中。但请务必遵循最佳做法9。

public void wrapException(String input)throws MyBusinessException {
尝试 {
// 做一点事
} catch(NumberFormatException e){
抛出 新的 MyBusinessException(“描述错误的消息。”,e);
}
}

因此,如果您想要处理它,只捕获异常。否则,在方法签名中指定它并让调用者处理它。

9.在没有消费的情况下包装例外

有时候捕获标准异常并将其包装成自定义异常会更好。此类异常的典型示例是应用程序或框架特定的业务异常。这允许您添加其他信息,还可以为异常类实现特殊处理。

执行此操作时,请确保将原始异常设置为原因。该异常类提供了接受一个特定的构造方法的Throwable作为参数。否则,您将丢失原始异常的堆栈跟踪和消息,这将导致难以分析导致异常的异常事件。

public void wrapException(String input)throws MyBusinessException {
尝试 {
// 做一点事
} catch(NumberFormatException e){
抛出 新的 MyBusinessException(“描述错误的消息。”,e);
}
}

摘要

正如您所看到的,当您抛出或捕获异常时,您应该考虑许多不同的事情。其中大多数都旨在提高代码的可读性或API的可用性。

例外通常是错误处理机制和通信媒介同时。因此,您应该确保讨论要与同事一起应用的最佳实践和规则,以便每个人都能理解一般概念并以相同的方式使用它们。

numberformatexception是什么异常_处理Java异常的9个最佳实践相关推荐

  1. java 异常 最佳实践_关于JAVA异常处理的20个最佳实践

    在我们深入了解异常处理最佳实践的深层概念之前,让我们从一个最重要的概念开始,那就是理解在JAVA中有三种一般类型的可抛类: 检查性异常(checked exceptions).非检查性异常(unche ...

  2. java 大量数据保存_使用Java保存大量数据的最佳实践

    这是一个非常广泛的问题,所以答案也很广泛.解决方案取决于(至少)这三件事: >您的条目的大小 存储10,000,000个整数将需要大约40MiB的内存,而存储10,000,000 x 1KiB记 ...

  3. Java 异常处理的 9 个最佳实践

    Java 异常处理的 9 个最佳实践 原文地址:https://dzone.com/articles/9-... 翻译出处:https://www.oschina.net/trans... 在 Jav ...

  4. Java 中处理 Exception 的最佳实践

    Java 中处理 Exception 的最佳实践 在Java中处理异常并不是一个简单的事情.不仅仅初学者很难理解,即使一些有经验的开发者也需要花费很多时间来思考如何处理异常,包括需要处理哪些异常,怎样 ...

  5. 《转载》Java异常处理的10个最佳实践

    本文转载自 ImportNew - 挖坑的张师傅 异常处理在编写健壮的 Java 应用中扮演着非常重要的角色.异常处理并不是功能性需求,它需要优雅地处理任何错误情况,比如资源不可用.非法的输入.nul ...

  6. 关于JAVA异常处理的20个最佳实践

    关于JAVA异常处理的20个最佳实践 在我们深入了解异常处理最佳实践的深层概念之前,让我们从一个最重要的概念开始,那就是理解在JAVA中有三种一般类型的可抛类: 检查性异常(checked excep ...

  7. 小菜:Java异常处理的10个最佳实践

    转载自   小菜:Java异常处理的10个最佳实践 异常处理在编写健壮的 Java 应用中扮演着非常重要的角色.异常处理并不是功能性需求,它需要优雅地处理任何错误情况,比如资源不可用.非法的输入.nu ...

  8. JAVA应用开发MQ实战最佳实践——Series2:消息队列RocketMQ性能测试案例

    简介:JAVA应用开发MQ实战最佳实践--Series2:消息队列RocketMQ性能测试案例 往期内容 JAVA应用开发MQ实战最佳实践--Series1:RocketMQ综述及代码设计 1. 消息 ...

  9. java异常_聊聊Java中的异常及处理

    前言 在编程中异常报错是不可避免的.特别是在学习某个语言初期,看到异常报错就抓耳挠腮,常常开玩笑说编程1分钟,改bug1小时.今天就让我们来看看什么是异常和怎么合理的处理异常吧! 异常与error介绍 ...

最新文章

  1. 【C++】Google C++编码规范(一):作用域
  2. search result
  3. python——文件和数据格式化
  4. JS-String方法
  5. SQLMAP使用笔记
  6. 【详细解读】进程管理 -死锁问题 系统有三个进程:A B C 这3个进程都需要5个系统资源。如果系统至少有多少个资源,则不可能发生死锁
  7. centos mysql php tomcat_Linux 安装JDK Tomcat MySQL的教程(使用Mac远程访问)
  8. 职称计算机承诺书,职称申报承诺书范本
  9. linux监控采集项
  10. linux查看是哪个端口,linux 查看哪个端口使用情况
  11. Blas SGEMM launch failed
  12. 苹果手机传照片到电脑_如何将苹果手机的照片和视频导到电脑上?小白看过来哦...
  13. Java基础(五):数组和Java方法
  14. sparkSql使用hive数据源
  15. 计算机术语翻译的最烂,我国计算机名词的翻译现状和建议
  16. c#定时器Timer
  17. cad修改快捷键_CAD自定义修改快捷键
  18. 朴素贝叶斯实战:人群收入预测(基于美国人口普查收入数据)
  19. Android 图片倒影
  20. 电商策略2----超卖、少卖

热门文章

  1. perl-regexp_使用Regexp :: Common在Perl中轻松进行数据验证
  2. Lovesource博士:或者我是如何学会不再担心和热爱开放的
  3. 软件自动化测试成功之道_是什么使测试自动化成功?
  4. opensource项目_最佳Opensource.com:教程
  5. jQuery 设计和自定义一个带展开动画效果的导航栏
  6. 程序员秒懂的30个段子:看到第几个你笑了?
  7. es6 async函数实例:按顺序完成异步操作
  8. es6 方法的 name 属性
  9. 用户代码未处理nullreferenceexception_CSAPP 第九章整理 未完成
  10. 【Python3爬虫】快就完事了--使用Celery加速你的爬虫