本文介绍了何时选择已检查和未检查的异常的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在 Java(或任何其他具有已检查异常的语言)中,在创建自己的异常类时,您如何决定是否应检查或取消检查?

In Java (or any other language with checked exceptions), when creating your own exception class, how do you decide whether it should be checked or unchecked?

我的直觉是说在调用者可能能够以某种富有成效的方式恢复的情况下会调用已检查的异常,而对于不可恢复的情况,未检查的异常会更多,但我会感兴趣别人的想法.

My instinct is to say that a checked exception would be called for in cases where the caller might be able to recover in some productive way, where as an unchecked exception would be more for unrecoverable cases, but I'd be interested in other's thoughts.

推荐答案

Checked Exceptions 很棒,只要您了解何时应该使用它们.Java 核心 API 未能遵循 SQLException(有时是 IOException)的这些规则,这就是它们如此糟糕的原因.

Checked Exceptions are great, so long as you understand when they should be used. The Java core API fails to follow these rules for SQLException (and sometimes for IOException) which is why they are so terrible.

Checked Exceptions 应该用于可预测,但不可预防的错误,可以从中恢复.

Checked Exceptions should be used for predictable, but unpreventable errors that are reasonable to recover from.

Unchecked Exceptions 应该用于其他所有事情.

Unchecked Exceptions should be used for everything else.

我会为你分解一下,因为大多数人都误解了这意味着什么.

I'll break this down for you, because most people misunderstand what this means.

  1. 可预测但不可预防:调用者尽其所能验证输入参数,但某些超出其控制范围的情况导致操作失败.例如,您尝试读取一个文件,但在您检查文件是否存在和读取操作开始之间,有人将其删除.通过声明一个已检查的异常,您是在告诉调用者预料到这次失败.
  2. 合理恢复:告诉调用者预测他们无法恢复的异常是没有意义的.如果用户试图读取一个不存在的文件,调用者可以提示他们输入一个新的文件名.另一方面,如果方法由于编程错误(无效的方法参数或错误的方法实现)而失败,则应用程序无法在执行中修复问题.它所能做的最好的事情就是记录问题并等待开发者稍后修复它.
  1. Predictable but unpreventable: The caller did everything within their power to validate the input parameters, but some condition outside their control has caused the operation to fail. For example, you try reading a file but someone deletes it between the time you check if it exists and the time the read operation begins. By declaring a checked exception, you are telling the caller to anticipate this failure.
  2. Reasonable to recover from: There is no point telling callers to anticipate exceptions that they cannot recover from. If a user attempts to read from an non-existing file, the caller can prompt them for a new filename. On the other hand, if the method fails due to a programming bug (invalid method arguments or buggy method implementation) there is nothing the application can do to fix the problem in mid-execution. The best it can do is log the problem and wait for the developer to fix it at a later time.

除非您抛出的异常满足上述所有条件,否则它应该使用未经检查的异常.

Unless the exception you are throwing meets all of the above conditions it should use an Unchecked Exception.

在每个级别重新评估:有时捕获已检查异常的方法不是处理错误的正确位置.在这种情况下,请考虑对您自己的来电者来说什么是合理的.如果异常是可预测的、不可预防的并且可以合理地让他们从中恢复,那么您应该自己抛出一个已检查的异常.如果没有,您应该将异常包装在未经检查的异常中.如果您遵循此规则,您会发现自己将检查异常转换为未检查异常,反之亦然,具体取决于您所在的层.

Reevaluate at every level: Sometimes the method catching the checked exception isn't the right place to handle the error. In that case, consider what is reasonable for your own callers. If the exception is predictable, unpreventable and reasonable for them to recover from then you should throw a checked exception yourself. If not, you should wrap the exception in an unchecked exception. If you follow this rule you will find yourself converting checked exceptions to unchecked exceptions and vice versa depending on what layer you are in.

对于已检查和未检查的异常,使用正确的抽象级别.例如,具有两种不同实现(数据库和文件系统)的代码存储库应该避免通过抛出 SQLExceptionIOException 来暴露特定于实现的细节.相反,它应该将异常包装在一个跨越所有实现的抽象中(例如 RepositoryException).

For both checked and unchecked exceptions, use the right abstraction level. For example, a code repository with two different implementations (database and filesystem) should avoid exposing implementation-specific details by throwing SQLException or IOException. Instead, it should wrap the exception in an abstraction that spans all implementations (e.g. RepositoryException).

这篇关于何时选择已检查和未检查的异常的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-28 04:43