【问题标题】:FindBugs - how to solve EQ_COMPARETO_USE_OBJECT_EQUALSFindBugs - 如何解决 EQ_COMPARETO_USE_OBJECT_EQUALS
【发布时间】:2011-02-06 05:34:57
【问题描述】:

我在这里一无所知...

 1: private static class ForeignKeyConstraint implements Comparable<ForeignKeyConstraint> {
 2: String tableName;
 3: String fkFieldName;
 4: 
 5: public int compareTo(ForeignKeyConstraint o) {
 6:    if (this.tableName.compareTo(o.tableName) == 0) {
 7:            return this.fkFieldName.compareTo(o.fkFieldName);
 8:        }
 9:        return this.tableName.compareTo(o.tableName);
10:    }
11: }

在第 6 行,我从 FindBugs 获得:Bug: net.blabla.SqlFixer$ForeignKeyConstraint defines compareTo(SqlFixer$ForeignKeyConstraint) and uses Object.equals()

Link to definition

我不知道如何改正。

【问题讨论】:

    标签: java findbugs compareto


    【解决方案1】:

    此错误意味着您没有在ForeignKeyConstraint 中覆盖equals(因此从Object 继承equals)所以以下不正确(来自compareTo 的javadoc):

    强烈建议但不严格要求(x.compareTo(y)==0) == (x.equals(y))。一般来说,任何实现了 Comparable 接口并违反此条件的类都应该清楚地表明这一事实。推荐的语言是“注意:这个类有一个与equals不一致的自然顺序。”

    要修复 FindBugs 检查,请覆盖 equals - 和 hashCode - 如果通常情况下有意义(或排除对此类的检查并使用建议的注释记录您的类违反此条件)。

    【讨论】:

      【解决方案2】:

      您是否尝试过在 SqlFixer.ForeignKeyConstraint 中也覆盖 equals 方法?

      我相信警告的基础是,如定义中所述,如果您覆盖 compareTo 而不是 equals,可能会发生奇怪的事情。

      欲了解更多信息,请查看Joshua Bloch's Effective Java, 2nd Edition。第 12 条更深入地介绍了实现 Comparable 的来龙去脉以及需要注意的一些事项。

      【讨论】:

        【解决方案3】:

        你可以通过实现一个 equals() 方法来解决它。参考 FindBugs 定义:

        “一般情况下,当且仅当equals返回true时,compareTo的值才应该返回零。如果违反这一点,就会在PriorityQueue等类中出现奇怪且不可预知的失败。”

        “强烈建议,但不严格要求 (x.compareTo(y)==0) == (x.equals(y))。”

        另一个例子是 TreeSet。它通过调用compareTo实现相等性检查,与equals不一致的compareTo实现使得TreeSet违反了Set接口的约定,可能导致程序故障。

        【讨论】:

          【解决方案4】:

          它告诉您 compareTo() 和 equals() 可能存在分歧。他们应该,真的,永远不要不同意。

          equals() 方法继承自 java.lang.Object,默认情况下检查两个对象是否相同instance。您的 compareTo 方法是基于 tableName 和 fkFieldName 比较对象。因此,您可能会发现自己处于这样一种情况:compareTo 声明两个对象相同(因为 tableName 和 fkFieldName 匹配),但 equals 声明它们不同(因为它们是不同的实例)。

          有一些 java API 依赖于 compareTo 和 equals 的一致性;这是 java 语言的一部分,被认为是核心语言契约。理想情况下,实现一个 equals(和 hashcode)方法来检查基于 tableName 和 fkFieldName 的相等性。

          【讨论】:

            【解决方案5】:

            Findbugs 很高兴:

            public int compareTo(ForeignKeyConstraint o) {
                if (this.equals(o)) {
                    return 0;
                } else if (this.tableName.equals(o.tableName)) {
                    // fkFieldName must be different
                    return this.fkFieldName.compareTo(o.fkFieldName);
                } else {
                    // tableName must be different
                    return this.tableName.compareTo(o.tableName);
                }
            }
            
            @Override
            public equals() {
              ...
            }
            
            @Override
            public int hashCode() {
              ...
            }
            

            【讨论】:

              猜你喜欢
              • 2012-12-26
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 2017-05-26
              • 2018-06-01
              相关资源
              最近更新 更多