기본 자료형(byte/short/int/long/char/float/double)에서 '=='는 실제 저장된 값을 비교하는 비교연산자로 쓰였다.
하지만 참조형(Stirng,배열,클래스,인터페이스)에서 '=='는 주소를 비교하는 주소비교연산자로 쓰인다.
(단, 같은 클래스 타입끼리만 비교가 가능하다.)
▲ 우선 기본자료형부터 비교연산자를 이용해 비교해보자. 당연히 똑같은 20을 가지고 있으므로 '같다'가 나올 것이다.
이번에는 참조형에서 사용을 위해 클래스형을 사용해보자.
▲ 두 종류의 클래스를 만들고 인스턴스화(객체화)(메모리 할당)까지 해주었다.
▲ 클래스가 다른 a와 b의 주소를 비교하려고 했더니 'Incompatible operand types A and B' error가 나면서 비교가 되질 않는다. 당연히 위에서 언급한 타입이 즉, 자료형이 즉, 클래스가 다르기 때문에 비교할 수 없는 것이다.
하지만 equals()메소드를 사용하면 타입이 다르더라도 비교할 수 있다.
▲ equals()메소드를 사용하면 타입에 구애받지않고 비교할 수 있다.
▲ ClassA타입의 a1을 하나 더 만들고 기존의 a와 비교해보면 비교를 할 수 있다. 같은 타입의 클래스이기 때문이다.
▲ 하지만 당연히 주소는 다를 것이다. 서로 다른 메모리의 주소를 참조(reference)하고 있을 것이므로.
▲ 같은 타입끼리는 주소대입연산도 가능하다. a에게 a1의 주소를 대입할 수 있는 것이다. 주소를 대입해주면 결국 같은 주소값을 가질 것이므로 "주소가 같다"가 출력될 것이며 결과는 아래와 같다.
▲ a의 주소가 a1과 같아진 것을 볼 수 있다.
▲ 타입이 다르면 주소비교연산도 안되는 것처럼 주소대입연산도 일반적으로 불가능하다. 하지만 타입이 다른 클래스간에 상속관계가 존재하면 대입과 형변환이 가능해진다. 여기서 a와 b는 상속관계가 아니기 때문에 주소대입이 불가하다.
이번에는 String클래스에서 비교연산자(==)를 사용해보자.
▲ String타입의 클래스를 두개만들고 객체화까지 하고 각각에는 같은 데이터값인 JAVA를 넣어주었다.
참조형에서는 ==를 사용하면 주소를 비교한다고 했으므로 str1==str2는 false가 나올 것이다.
equals()메소드를 사용해서 str1과 str2를 비교하면 주소가 다르므로 false가 나와야 하는데 true가 출력된다.
원래 Object에서는 주소값을 비교하는 기능의 메소드이지만, String클래스에서 equals()메소드를 사용할 때는 오버라이딩되어 실제 데이터값을 비교하는 기능으로 바뀌기 때문이다.
▲ 이번에는 new연산자를 사용하지 않고 바로 문자열을 대입해보았다.
str3와 str4의 주소값을 비교해보면 true가 나온다. new연산자를 사용하지 않았기 때문에 각각의 새로운 메모리가 생성되지 않았고 같은 메모리를 참조하고 있기 때문이다.
▲ 일반적인 클래스에서 .toString을 사용하면 주소값을 반환해주는데, Stirng클래스에서는 역시나 오버라이딩 되어있어 주소값이 아닌 실제 데이터값을 반환하는 기능으로 작동한다. 때문에 우리는 str5에 저장되어 있는 주소값(String@ox11234와 같은 주소값)을 직접적으로 볼 수없고 다만 hashcode()메소드 같은 메소드를 이용하여 십진수로 바뀐 주소와 같이 간접적으로 밖에 알 수 없다.
'Java' 카테고리의 다른 글
[Java]Regular Expression(정규표현식) (0) | 2022.03.10 |
---|---|
[Java]String Buffer (0) | 2022.03.09 |
[Java]Wrapper class - part.3(Character) (0) | 2022.03.08 |
[Java]Wrapper class - part.2(Integer) (0) | 2022.03.08 |
[Java]Wrapper class - part.1 (0) | 2022.03.08 |