[JAVA] Object 클래스의 toString(), equals(), hashCode()

yekyeong·2021년 8월 7일
0

Java

목록 보기
2/2

Object 클래스

Java Document에서는 Object 클래스를 다음과 같이 정의한다.
Object는 모든 클래스의 최상위 클래스로, 모든 클래스는 Object 클래스를 상속받고 있다.

Object 클래스가 가지고 있는 메소드는 다음과 같다.

  • public boolean equals(Object obj)
  • protected void finalize()
  • public Class<?> getClass()
  • public int hashCode()
  • public void notify()
  • public void notifyAll()
  • public String toString()
  • public void wait()
  • public void wait(long timeout)
  • public void wait(long timeout, int nanos)

모든 클래스는 Object를 상속받는다고 했기 때문에 자바의 모든 객체는 위 메소드를 가지고 있다고 할 수 있다. 이 중에서 자주 사용되는 toString(), equals(), hashCode()를 오늘 중점적으로 살펴보겠다.


toString()

toString()은 객체를 문자열로 표현하는 메소드이다.

디폴트 동작 : getClass().getName() + '@' + Integer.toHexString(hashCode())

해당 메소드는 overriding을 해서 객체의 상태를 쉽게 파악할 수 있게 한다.

// overriding(재정의) 이전

package com.programmers.java;

public class User {
    private int age;
    private String name;

    public User(int age, String name) {
        this.age = age;
        this.name = name;
    }

    public static void main(String[] args) {
        User user = new User(27, "Emily");
        System.out.println(user.toString());
    }
}

-> 실행 결과 : com.programmers.java.User@1dbd16a6

// overriding(재정의) 이후

package com.programmers.java;

public class User {
    private int age;
    private String name;

    public User(int age, String name) {
        this.age = age;
        this.name = name;
    }

    @Override
    public String toString() {
        return "User{" +
                "age=" + age +
                ", name='" + name + '\'' +
                '}';
    }

    public static void main(String[] args) {
        User user = new User(27, "Emily");
        System.out.println(user.toString());
    }
}

-> 실행 결과 : User{age=27, name='Emily'}


equals()

equals()는 두 객체가 같은지 다른지 나타내는 메소드이다.

디폴트 동작 : 두 객체가 주소 값이 동일하다면 true를, 다르다면 false를 리턴('==' 연산 결과)

해당 메소드를 override하면 객체가 메모리에서 같은 주소를 갖는 '물리적 동일함' 뿐만 아니라 같은 age의 사용자 객체, 같은 id의 상품 객체와 같이 같은 내용을 갖는 '논리적 동일함'까지 비교할 수 있게 된다.

// overriding(재정의) 이전

package com.programmers.java;

public class User {
    private int age;
    private String name;

    public User(int age, String name) {
        this.age = age;
        this.name = name;
    }

    public static void main(String[] args) {
        User user = new User(27, "Emily");
        User user2 = new User(27, "Emily");
        System.out.println(user.equals(user2));
    }
}

-> 실행 결과 : false

// overriding(재정의) 이후

package com.programmers.java;

public class User {
    int age;
    String name;

    public User(int age, String name) {
        this.age = age;
        this.name = name;
    }

    @Override
    public boolean equals(Object o) {
        if(this.age == ((User)o).age && this.name == ((User)o).name)
            return true;
        return false;
    }

    public static void main(String[] args) {
        User user = new User(27, "Emily");
        User user2 = new User(27, "Emily");
        System.out.println(user.equals(user2));
    }
}

-> 실행 결과 : true

일반적으로 이 메소드를 재정의할 때마다 다음으로 설명할 hashCode()도 재정의해서 hashCode()에 대한 일반 계약을 유지할 수 있게 해야한다.


hashCode()

hashCode()는 객체의 고유한 값(해시코드)을 나타내는 메소드이다.

디폴트 동작 : JVM이 부여한 코드 값을 리턴

hashCode()의 일반 계약 중 하나가 'equals() 메소드에 따라 두 개체가 동일한 경우 두 개체 각각에 대해 hashCode() 메소드를 호출하면 동일한 정수 결과가 생성되어야 한다.'는 것이다. 이 말을 다시 풀어 정리하자면...

  • hashCode()를 실행해 나온 해시코드 값이 다르다 -> 다른 객체
  • equals() 실행 값이 true라면 두 객체의 hashCode() 실행 결과도 같다 -> 같은 객체
  • hashCode()를 실행해 나온 해시코드 값이 같을지언정 equals() 실행 결과가 false가 나올 수 있다 -> 다른 객체

위 설명을 바탕으로 그림을 그려 표현하면 아래와 같다.


(참고)

profile
2년차 백엔드 개발자

0개의 댓글

관련 채용 정보