1

我有一个关于 Java 最佳实践的问题。我正在写一个类,它非常依赖于构造中的对象。事实上,如果在构造时传入的对象为空,那么大部分功能都没有意义。我认为最好在对象构造时将 null 作为参数传递的情况下抛出异常,但我不知道在这种情况下最合适的异常是什么。我应该抛出 NullPointer、IllegalArgument、Instatiation 还是初始化异常。

我已经看到这些都在整个 Java 源代码库中使用,我似乎无法区分为什么在某些情况下使用 NullPointer 而在其他情况下使用 IllegalArgument。我个人会认为,如果在构造时传入了错误的参数,则应该会发生一些初始化错误。

4

4 回答 4

5

首先,您绝对应该抛出异常。这只是正确的事情。

至于你应该扔IllegalArgumentException还是NullPointerException- Josh Bloch 在 Effective Java 中谈到了这一点,并普遍认为这NullPointerException是一个合理的选择。我不完全确定我是否同意(我可能会选择IllegalArgumentException),但最终这不太重要:您不应该直接捕获这些异常中的任何一个,并且堆栈跟踪会告诉您哪里有问题。

(很遗憾 Java 没有与 .NET 等效的 .NET ArgumentNullException,这意味着它听起来的样子。)

就我个人而言,我是 Guava 课程的忠实粉丝Preconditions

public class Foo {
  private final Bar bar;

  public Foo(Bar bar) {
    this.bar = Preconditions.checkNotNull(bar);
  }
}

(有时与 . 的静态导入一起使用checkNotNull。)

于 2012-06-22T16:47:36.763 回答
4

IllegalArgument 向使用该代码的开发人员清楚地说明了问题是什么以及如何解决它。它还清楚地表明,如果没有该对象,该方法将无法工作。

NullPointer 意味着他们必须考虑一下问题是什么(不多),并且可能意味着代码更干净,但就像我上面所说的那样。从文档的角度来看,尚不清楚您的代码是否可以使用空值。

于 2012-06-22T16:50:50.770 回答
1

NullPointerException当您期望一个有效的对象但得到null而不是使用时。这在尝试调用null对象上的方法时尤其相关。这是它最常见的用途。但是,您的情况也可能有必要。

IllegalArgumentException当您收到的参数不是您期望的或错误的类型/样式/等时使用。在我看来,这在你的情况下会更合适。您期望一个有效的对象,但您收到null了一个参数。这个参数值是无效的 - 所以我会抛出IllegalArgumentException并在异常的消息中指定什么是错误的,例如:

public MyClass(InputObject obj) {
    if(obj == null) {
        throw new IllegalArgumentException("null passed to MyClass constructor");
    }

    ...
}
于 2012-06-22T16:49:24.767 回答
1

如果您认为平台异常没有为客户提供正确数量的信息来理解和解决问题,您可以创建自己的在这方面更合适的异常,比如 .NET 的ArgumentNullException;这将告诉客户问题是什么以及如何解决它

于 2012-06-22T22:45:26.153 回答