인프런 커뮤니티 질문&답변

작성자 없음

작성자 정보가 삭제된 글입니다.

김영한의 실전 자바 - 중급 1편

equals() - 2. 구현

equals 설계가 이해가 어렵습니다

작성

·

74

·

수정됨

0

 [질문 템플릿]
1. 강의 내용과 관련된 질문인가요? (예/아니오)
2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예/아니오)
3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예/아니오)

[질문 내용]
equals는 매개변수를 받으면

-> User2 클래스로 변환 (다운캐스팅)

-> 만들어진 User2객체에서 id 추출

-> 그걸 User2 id와 비교

정리하면 들어온 Object를 User2로 바꾸어 id를 확인하는 메서드인데

User2를 User2로 다운캐스팅하여 User2와 비교 후 User1 과 비교하는 로직 아닌가요?

어느부분이 잘못된건지 모르겠습니다ㅜㅜ

답변 2

1

질문 내용이 명확하지 않아서 어려움을 느끼시는 부분이 어떤 지점인지는 알 수 없으나, 제가 스스로의 이해를 위해서 작성했던 코드를 확인하시면 도움이 될 것 같아 첨부합니다.

package mytest.equality;

public class UserMain {

    public static void main(String[] args) {
        User user1 = new User("id-100");
        User user2 = new User("id-100");

        // prints false
        System.out.println(user1.equals(user2));
        
        // test code
        System.out.println(user1); // this
        // ㄴ prints mytest.equality.User@30f39991
        System.out.println(user2); // obj
        // ㄴ prints mytest.equality.User@452b3a41
        System.out.println(user1 == user2); // 당연히 false
    }
}
package mytest.equality;

public class User {

    private String id;

    public User(String id) {
        this.id = id;
    }
    
    @Override
    public boolean equals(Object o) {
        // 1. 
        // 위 UserMain에서 본 것과 같이 this와 o는 각각 user1, user2의
        // 패키지.클래스@해시코드를 리턴함 즉, physical address를 리턴함.
        // 이 둘이 같다면 아예 동일한 객체이므로 당연히 동등하기도 함.
        if (this == o) return true;
        
        // 2. 아래 해설 코드 확인
        if (o == null || getClass() != o.getClass()) return false;
        
        // 여기까지 도달했다면, user1과 user2 객체는
        // `패키지.클래스`는 동일하지만, 해시코드는 동일하지 않은 상태라는 것이 보증됨.
        // 3.
        // 해당 클래스에서는 User의 field인 id값이 동일하다면 동등한 객체로 판단하기로 정했음.
        // 따라서 User field인 id에 접근해야 하는데, 
        // 참조 타입이 Object type(부모)인 상태로는 id(자식)에 접근할 수 없음.
        // 따라서 down-casting
        User user = (User) o;
        
        // 4.
        // 두 객체의 id 값이 동일한지 확인.
        // 맞다면 동등한 객체이고, 아니라면 동등하지 않은 객체임.
        return id == user.id;
        // ㄴ (this.id) == (user.id);와 같은 의미임.
}
// 위 코드 블록의 2.에 대한 해설 코드

// o == null
// ㄴ 비교하려는 객체가 null 즉 없는 상태라면, 당연히 동일/동등하지 않음.

// getClass()는 다음과 같음
System.out.println(user1.getClass());
// ㄴ prints class mytest.equality.User

// o.getClass()는 다음과 같음
System.out.println(user2.getClass());
// ㄴ prints class mytest.equality.User

// getClass()는 해당 객체의 `패키지.클래스`를 리턴함.
// 이 값이 동일하지 않다면 해시코드는 확인할 필요도 없이 동일/동등하지 않은 객체임.

0

안녕하세요, 인프런 AI 인턴입니다. ssseo215님.

equals 메서드에 대한 이해가 어렵다고 하셨군요. User 클래스를 직접 설계하지 않고, Object 클래스의 equals 메서드를 오버라이드하거나 사용하는 방식으로 이해를 돕기 위해 관련 질문과 답변을 확인해 보시길 권장드립니다. 다음 링크를 통해 자세한 내용을 참고하시면 좋을 것 같습니다.

관련 질문들:

  1. findOne()코드를 직접 짜보고 테스트를 해보았는데 오류가 납니다.

  2. 프록시 관련한 equals()오버라이딩, 제가 이해한 것이 맞나요?

    • 인스턴스의 클래스를 비교할 때 instanceof를 사용하는 이유와 getter를 사용하는 방식을 설명합니다.
  3. 동일성 비교 실패

    • 동일성 비교에 대한 JPA의 프록시 문제와 이를 해결하는 방법에 대해 상세히 설명합니다.

질문에서 언급된 내용처럼, equals 메소드는 대상 객체를 적절히 다운캐스팅한 후 필요한 필드 값을 비교합니다. Object를 매개변수로 받는 이유는 equals 메소드가 어떤 클래스의 객체를 비교할 때, 해당 클래스의 객체뿐만 아니라 상속받은 모든 객체와의 비교를 가능하게 하기 위해서입니다.

저는 질문자님의 이해를 돕고자 지식공유자님의 기존 답변을 참고하여 유사한 답변 링크를 추천해드리고 있습니다.
현재 베타 기능으로 답변이 만족스럽지 않을 수 있는 점 양해 부탁드립니다. 🙏
추가적으로 궁금한 점이 있으시면, 이어서 질문해 주세요. 곧 지식공유자께서 답변해 주실 것입니다.

작성자 없음

작성자 정보가 삭제된 글입니다.

질문하기