Programing

java equals () 메소드 재정의-작동하지 않습니까?

lottogame 2020. 6. 12. 22:03
반응형

java equals () 메소드 재정의-작동하지 않습니까?


나는 equals()오늘 시험 법 에 대한 흥미롭고 매우 실망스러운 문제 에 부딪쳤다.

완벽 함을 위해 IDE 또는 디버거를 사용하지 않았습니다. 좋은 구식 텍스트 편집기와 System.out입니다. 시간은 매우 제한되어 있었고 학교 프로젝트였습니다.

어쨌든-

나는 포함 할 수있는 기본적인 쇼핑 카트를 개발하고 ArrayListBook객체 . 구현하기 위해 addBook(), removeBook()그리고 hasBook()카트의 방법을, 나는 여부를 확인하고 싶었다 Book이미 존재 Cart. 그래서 나는 간다-

public boolean equals(Book b) {
    ... // More code here - null checks
    if (b.getID() == this.getID()) return true;
    else return false;
}

테스트에서 모두 잘 작동합니다. 6 개의 객체를 만들어 데이터로 채 웁니다. 에 대해 많은 추가, 제거, has () 작업을 수행하면 Cart모든 것이 잘 작동합니다. 나는 당신이 할 수있는 읽기 중 하나가 equals(TYPE var)또는equals(Object o) { (CAST) var } 하지만이 작동 된 이후, 너무 많이 중요하지 않았다 것으로 가정.

그럼 난 문제로 실행 - 내가 만드는 데 필요한 Book와 개체를 ID Book 클래스 내에서한다. 다른 데이터는 입력되지 않습니다. 기본적으로 다음과 같습니다.

public boolean hasBook(int i) {
    Book b = new Book(i);
    return hasBook(b);
}

public boolean hasBook(Book b) {
    // .. more code here
    return this.books.contains(b);
}

갑자기 equals(Book b)방법이 더 이상 작동하지 않습니다. 좋은 디버거없이 추적하는 데 시간이 오래 걸렸으며 Cart클래스가 올바르게 테스트되고 수정 되었다고 가정합니다 . equals()다음과 같은 방법으로 스와핑 한 후 :

public boolean equals(Object o) {
    Book b = (Book) o;
    ... // The rest goes here   
}

모든 것이 다시 작동하기 시작했습니다. 방법이 명확에도 예약 매개 변수를 취할하지 않기로 결정 이유가 거기에 있었다Book 목적은? 유일한 차이점은 동일한 클래스 내에서 인스턴스화되었으며 하나의 데이터 멤버로 채워진 것 같습니다. 매우 혼란 스러워요. 제발, 빛 좀 비춰?


Java에서 equals()상속 된 메소드 Object는 다음과 같습니다.

public boolean equals(Object other);

즉, 매개 변수는 유형이어야합니다 Object.

ArrayList항상 제대로 대체하지 않은 한 호출 된 경우, 올바른 equals 메소드를 사용 Object의 같음.

메소드를 올바르게 재정의하지 않으면 문제가 발생할 수 있습니다.

매번 다음을 무시합니다.

@Override
public boolean equals(Object other){
    if (other == null) return false;
    if (other == this) return true;
    if (!(other instanceof MyClass))return false;
    MyClass otherMyClass = (MyClass)other;
    ...test other properties here...
}

@Override주석을 사용하면 바보 같은 실수로 많은 도움이 될 수 있습니다.

수퍼 클래스 또는 인터페이스의 메서드를 재정의한다고 생각 될 때마다 사용하십시오. 그렇게하면 잘못하면 컴파일 오류가 발생합니다.


일식을 사용하는 경우 상단 메뉴로 이동하십시오.

소스-> equals () 및 hashCode () 생성


귀하의 질문에 약간의 주제가 없지만 어쨌든 언급 할 가치가 있습니다.

Commons Lang 은 equals와 hashcode를 재정의하는 데 사용할 수있는 훌륭한 방법을 가지고 있습니다. 체크 아웃 EqualsBuilder.reflectionEquals (...)HashCodeBuilder.reflectionHashCode (...) . 과거에 많은 두통을 피했습니다. 물론 ID에서 "동일"을 원한다면 상황에 맞지 않을 수 있습니다.

또한 @Overrideequals (또는 다른 방법)를 재정의 할 때마다 주석 을 사용해야한다는 것에 동의합니다 .


Another fast solution that saves boilerplate code is Lombok EqualsAndHashCode annotation. It is easy, elegant and customizable. And does not depends on the IDE. For example;

import lombok.EqualsAndHashCode;

@EqualsAndHashCode(of={"errorNumber","messageCode"}) // Will only use this fields to generate equals.
public class ErrorMessage{

    private long        errorNumber;
    private int         numberOfParameters;
    private Level       loggingLevel;
    private String      messageCode;

See the options avaliable to customize which fields to use in the equals. Lombok is avalaible in maven. Just add it with provided scope:

<dependency>
    <groupId>org.projectlombok</groupId>
    <artifactId>lombok</artifactId>
    <version>1.14.8</version>
    <scope>provided</scope>
</dependency>

in Android Studio is alt + insert ---> equals and hashCode

Example:

    @Override
public boolean equals(Object o) {
    if (this == o) return true;
    if (o == null || getClass() != o.getClass()) return false;

    Proveedor proveedor = (Proveedor) o;

    return getId() == proveedor.getId();

}

@Override
public int hashCode() {
    return getId();
}

Consider:

Object obj = new Book();
obj.equals("hi");
// Oh noes! What happens now? Can't call it with a String that isn't a Book...

the instanceOf statement is often used in implementation of equals.

This is a popular pitfall !

The problem is that using instanceOf violates the rule of symmetry:

(object1.equals(object2) == true) if and only if (object2.equals(object1))

if the first equals is true, and object2 is an instance of a subclass of the class where obj1 belongs to, then the second equals will return false!

if the regarded class where ob1 belongs to is declared as final, then this problem can not arise, but in general, you should test as follows:

this.getClass() != otherObject.getClass(); if not, return false, otherwise test the fields to compare for equality!


recordId is property of the object

@Override
    public boolean equals(Object obj) {
        if (this == obj)
            return true;
        if (obj == null)
            return false;
        if (getClass() != obj.getClass())
            return false;
        Nai_record other = (Nai_record) obj;
        if (recordId == null) {
            if (other.recordId != null)
                return false;
        } else if (!recordId.equals(other.recordId))
            return false;
        return true;
    }

참고URL : https://stackoverflow.com/questions/185937/overriding-the-java-equals-method-not-working

반응형