通常,如果不是总是这样,我们将if语句与==or!=运算符结合使用,以检查对象引用是否为null。我们这样做是为了验证传递给构造函数或方法的参数不包含空值。这些空检查在我们的代码中可以看作是混乱的。
解决的办法是使用java.util.Objects类。静态实用程序类提供了requireNonNull(T)和类似的方法,requireNonNull(T, String)以检查指定的对象引用是否不为null。如果为null,则这些方法将引发NullPointerException。使用第二种方法变体,我们可以自定义异常消息。
下面的示例显示了我们如何使用这些方法。
package org.nhooo.example.util;
import java.util.Objects;
public class ObjectsNullCheckDemo {
private String firstName;
private String lastName;
/**
* Validate constructor arguments. The firstName and lastName
* arguments can't be null. A NullPointerException with the
* specified message will be thrown.
*/
public ObjectsNullCheckDemo(String firstName, String lastName) {
this.firstName = Objects.requireNonNull(firstName,
"First name can't be null.");
this.lastName = Objects.requireNonNull(lastName,
"Last name can't be null.");
}
public void setFirstName(String firstName) {
// 名不能为空。
this.firstName = Objects.requireNonNull(firstName,
"First name can't be null.");
}
public void setLastName(String lastName) {
// 姓氏不能为空。
this.lastName = Objects.requireNonNull(lastName,
"Last name can't be null.");
}
public static void main(String[] args) {
// 这条线很好。
ObjectsNullCheckDemo demo = new ObjectsNullCheckDemo("John", "Doe");
System.out.println("demo = " + demo);
try {
// 该行产生一个NullPointerException
ObjectsNullCheckDemo demo1 = new ObjectsNullCheckDemo("Alice", null);
} catch (Exception e) {
e.printStackTrace();
}
String name = null;
try {
// 下面的行将抛出java.lang.NullPointerException。
Objects.requireNonNull(name);
} catch (Exception e) {
e.printStackTrace();
}
}
@Override
public String toString() {
return "ObjectsNullCheckDemo{" +
"firstName='" + firstName + '\'' +
", lastName='" + lastName + '\'' +
'}';
}
}运行上面的代码将打印以下结果:
demo = ObjectsNullCheckDemo{firstName='John', lastName='Doe'}
java.lang.NullPointerException: Last name can't be null.
at java.util.Objects.requireNonNull(Objects.java:228)
at org.nhooo.example.util.ObjectsNullCheckDemo.<init>(ObjectsNullCheckDemo.java:14)
at org.nhooo.example.util.ObjectsNullCheckDemo.main(ObjectsNullCheckDemo.java:34)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:483)
at com.intellij.rt.execution.application.AppMain.main(AppMain.java:144)
java.lang.NullPointerException
at java.util.Objects.requireNonNull(Objects.java:203)
at org.nhooo.example.util.ObjectsNullCheckDemo.main(ObjectsNullCheckDemo.java:42)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:483)
at com.intellij.rt.execution.application.AppMain.main(AppMain.java:144)