Java重写等于,数组

时间:2010-10-23 07:14:50

标签: java

这是我正在处理的代码,覆盖了equals。我没有尝试过编译,但Netbeans正在给我一个警告,说明不兼容类型的.equals。

public class Customers {
    private String name;

    public Customers(name) {
        this.name = name;
    }

    public boolean equals(String name) {
        return (this.name.equals(name));
    }
} 

主类

public class TestCustomers {
    public static void main(String args[]) {
       Customers cus = new Customers[1];
       cus[1] = new Customers("John");
       if(cus[1].equals("John")
           ...
    }
}

这可以正常工作而不使用Array。但是对于数组,它会向我显示警告。

为什么它会给我一个警告,说明。不兼容类型的.equals?这是因为Array中的Type Erasures吗?

先谢谢!

4 个答案:

答案 0 :(得分:4)

投诉可能是因为

public boolean equals(String name)

并没有真正覆盖Object.equals - 方法,因为Objects.equalsObject作为参数,而不是String。 (如果你习惯在你想要覆盖其他方法的方法前面明确地写@Override,这可能就很明显了。)

虽然Customer可以equalCustomer之外的所有内容,但对我来说似乎是一个非常糟糕的主意。我会做这样的事情:

class Customer {
    private String name;

    public Customer(String name) {
        this.name = String.valueOf(name);
    }

    public String getName() {
        return name;
    }

    @Override
    public boolean equals(Object o) {
        return (o instanceof Customer) && ((Customer) o).name.equals(name);
    }

    @Override
    public int hashCode() {
        return name.hashCode();
    }
} 

主要课程:

public class Main {
    public static void main(String args[]) {
        Customer[] cus = new Customer[1];
        cus[0] = new Customer("John");

        // Compare against name
        if (cus[0].getName().equals("John"))
            System.out.println("Name equals.");

        // Compare against another customer:
        if (cus[0].equals(new Customer("John")))
            System.out.println("Customer equals.");
     }
}

答案 1 :(得分:1)

// Wrong 

public boolean equals(String name) {
        return (this.name.equals(name));
}

// Correct Way to override equals from Object.


// How about this implementation.

public boolean equals(Object obj) {


               if ( obj == null )
                    return false;  

               if ( obj ==  this )
               { 
                    return true;
               }

              if  ( getClass() !=  obj.getClass())
              {
                    return false;
              }
              Customer cust = (Customer) obj;
              if  ( this.getName().equals(cust.getName()))
              {
                    return true;
              }
              else 
              {
                   return false;
              }
 }

然而,使用Apache Commons Equalsbuilder是进行深度检查的最佳方式。 http://commons.apache.org/lang/api-2.4/org/apache/commons/lang/builder/EqualsBuilder.html

答案 2 :(得分:0)

我觉得编译器抱怨的内容与重载无关(或者在你的情况下试图重载)equals

Customers cus = new Customers[1];
cus[1] = new Customers("John");
if (cus[1].equals("John")) {

此处的问题是cus已被声明为Customers而不是Customers[]。因此编译器对cus[1]的含义感到非常困惑,并且(可能)给它一个未定义的类型。然后它说未定义的类型不支持equals

如果你改变:

Customers cus = new Customers[1];

Customers[] cus = new Customers[1];

如果有一堆错误信息,包括(我怀疑)关于equals的错误消息,你就会摆脱它。然后,您需要返回并解决问题的定义equals ...以及其他错误,例如cus[1]会抛出ArrayIndexOutOfBoundException

  

为什么它会给我一个警告,说明。不兼容类型的.equals?

我认为您通过尝试索引类型不是数组的变量来设法混淆编译器;见上文。

  

由于阵列中的类型擦除,这是否与此有关?

没有。类型擦除问题仅将 应用于泛型类型;即涉及类型参数的类型。您没有任何类型参数。

答案 3 :(得分:-1)

  1. 将“cus”的类型更改为“Customers [] cus
    • Customers [] cus = ...
  2. 将String参数类型添加到Customers构造函数
  3. 访问项目0(零),而不是1(一) - Java数组中的第一项是索引0。
  4. 将“equals”方法参数类型更改为“Object”而不是String
  5. 添加“hashCode”方法 - 只要覆盖equals,就应该覆盖hashCode(参见“Effective Java”,第9项
  6. equals方法应具有以下属性(请参阅“Effective Java”,第8项)
    • o1.equals(null)== false
    • reflexive(x.equals(x)== true)
    • 对称;只有当y.equals(x)
    • 时,x.equals(y)才能返回true
    • 传递;如果o1.equals(o2)和o2.equals(o3),那么o1.equals(o3)
    • 相符; o1.equals(o2)必须始终返回相同的结果(假设两个对象都没有更改)
  7. “Effective Java”是一本很好的书,非常值得一读!