Java:在equals检查中避免NullPointerException的干净方法

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/5661936/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-30 12:09:02  来源:igfitidea点击:

Java: Clean way of avoiding NullPointerException in equals checks

javanullpointerexceptionequalscoding-style

提问by Svish

I have an address object that I want to create an equals method for. I could have made this quite simple by doing something like the following (shortened a bit):

我有一个地址对象,我想为其创建一个 equals 方法。我可以通过执行以下操作(稍微缩短一点)来使这变得非常简单:

public boolean equals(Object obj) 
{
    if (this == obj)
        return true;

    if (obj == null)
        return false;

    if (getClass() != obj.getClass())
        return false;

    Address other = (Address) obj;

    return this.getStreet().equals(other.getStreet())
        && this.getStreetNumber().equals(other.getStreetNumber())
        && this.getStreetLetter().equals(other.getStreetLetter())
        && this.getTown().equals(other.getTown());
}

Problem is, some of these might be null. I will in other words get a NullPointerExceptionif there is no street letter in this address.

问题是,其中一些可能为空。换句话说,NullPointerException如果这个地址中没有街道字母,我会得到一个。

How can I write this in a clean way while taking null values into account?

如何在考虑空值的同时以干净的方式编写它?

采纳答案by Peter Lawrey

You can use a helper method like

您可以使用辅助方法,例如

public static boolean isEqual(Object o1, Object o2) {
    return o1 == o2 || (o1 != null && o1.equals(o2));
}

回答by bdoughan

You could do the following:

您可以执行以下操作:

public boolean equals(Object obj) 
{
    if (this == obj) {
        return true;
    }

    if (obj == null) {
        return false;
    }

    if (getClass() != obj.getClass()) {
        return false;
    }

    Address other = (Address) obj;

    return equals(this.getStreet(),other.getStreet())
        && equals(this.getStreetNumber(), other.getStreetNumber())
        && equals(this.getStreetLetter(), other.getStreetLetter())
        && equals(this.getTown(), other.getTown());
}

private boolean equals(Object control, Object test) {
    if(null == control) {
        return null == test;
    }
    return control.equals(test);
}

Java 7 introduced built-in support for this use case with the java.util.Objects class see:

Java 7 通过 java.util.Objects 类引入了对此用例的内置支持,请参见:

回答by Jared Russell

Google Guavaprovides Objects.equal(Object, Object)which checks for equality while taking into consideration that either of the parameters might be null:

Google Guava提供了Objects.equal(Object, Object)来检查相等性,同时考虑到其中一个参数可能为空:

...
return Objects.equal(this.getStreet(), other.getStreet())
    && Objects.equal(this.getStreetNumber(), other.getStreetNumber())
    && Objects.equal(this.getStreetLetter(), other.getStreetLetter())
    && Objects.equal(this.getTown(), other.getTown());

It's also worth pointing out that Objects has other helper methods for implementing hashCode()and toString().

还值得指出的是 Objects 有其他帮助方法来实现 hashCode()toString()

回答by kliu

I have a helper class Checker w/ a static method:

我有一个带有静态方法的辅助类 Checker:

 public static boolean isEquals(final Object o1, final Object o2) {
        return o1 == null ? o2 == null : o1.equals(o2);
 }

so, in the equals method,

所以,在equals方法中,

 return Checker.isEquals(this.getStreet(), other.getStreet())
        && Checker.isEquals(this.getStreetNumber(), other.getStreetNumber())
        && Checker.isEquals(this.getStreetLetter(), other.getStreetLetter())
        && Checker.isEquals(this.getTown(), other.getTown());

回答by moritz

You can use Objects.equalfrom Googles guava or the EqualsBuilderfrom apache commons

您可以使用Googles guava 中的Objects.equal或apache commons 中的EqualsBuilder

回答by Michael Borgwardt

There is no really clean way to do that; the best option is probably to have your IDE generate the code for you. Eclipse can do it via the Source -> Generate hashCode() and equals() context menu.

没有真正干净的方法可以做到这一点。最好的选择可能是让您的 IDE 为您生成代码。Eclipse 可以通过 Source -> Generate hashCode() 和 equals() 上下文菜单来完成。

回答by Carlos Daniel Gadea Omelchenko

I'd consider defining some of the equals methods as static class methods, like say for the Street objects. This way you don't ever attempt to call the .equals() method on a null.

我会考虑将一些 equals 方法定义为静态类方法,比如 Street 对象。这样您就不会尝试在 null 上调用 .equals() 方法。

A sample function might look like:

示例函数可能如下所示:

public static boolean equals(Object one, Object two)

Also, it's good practice to put checks like

此外,将检查如

if (obj == null)
   return false;

at the very beginning of a function.

在函数的最开始。

回答by IanGilham

Apache Commons Langprovides the EqualsBuilderhelper class for equality comparissons. There is also one for hash codes.

Apache Commons Lang为相等比较提供了EqualsBuilder帮助器类。还有一个用于哈希码。

return new EqualsBuilder()
.append(this.getStreet(), other.getStreet())
.append(this.getStreetNumber(), other.getStreetNumber()
.append(this.getStreetLetter(), other.getStreetLetter())
.append(this.getTown(), other.getTown())).isEquals();