String 클래스는 자바에서 가장 많이 사용되는 클래스로써, new
연산자를 사용하지 않고도 인스턴스를 생성할 수 있다. 단, new
연산자를 이용하여 인스턴스를 생성할 때와, 직접 리터럴로 생성할 때 인스턴스가 생성되는 메모리 영역이 다르다.
String str1 = "hello";
String str2 = "hello";
new
연산자를 이용하지 않고 리터럴을 이용하여 참조변수를 선언하면, 객체는 메모리의 메서드 영역
에 생성된다.String str3 = new String("hello");
String str4 = new String("hello");
new
연산자를 이용하여 만든 객체는 메모리의 힙 영역
에 생성된다.public class StringExam {
public static void main(String[] args) {
String str1 = "hello"; // 메서드 영역에 객체(리터럴) 생성
String str2 = "hello";
String str3 = new String("hello"); // 힙 영역에 객체 생성
String str4 = new String("hello");
if (str1 == str2) {
System.out.println("str1과 str2는 같은 객체를 참조한다.");
} else {
System.out.println("str1과 str2는 다른 객체를 참조한다.");
}
if (str1 == str3) {
System.out.println("str1과 str3은 같은 객체를 참조한다.");
} else {
System.out.println("str1과 str3은 다른 객체를 참조한다.");
}
if (str3 == str4) {
System.out.println("str3과 str4는 같은 객체를 참조한다.");
} else {
System.out.println("str3과 str4는 다른 객체를 참조한다.");
}
if (str3.equals(str4)) {
System.out.println("str3과 str4가 참조하는 객체의 값은 같다.");
} else {
System.out.println("str3과 str4가 참조하는 객체의 값은 다르다.");
}
System.out.println("str1 hashcode: " + System.identityHashCode(str1)); // 985922955
System.out.println("str2 hashcode: " + System.identityHashCode(str2)); // 985922955
System.out.println("str3 hashcode: " + System.identityHashCode(str3)); // 586617651
System.out.println("str4 hashcode: " + System.identityHashCode(str4)); // 328638398
}
}
/*
(실행 결과)
str1과 str2는 같은 객체를 참조한다.
str1과 str3은 다른 객체를 참조한다.
str3과 str4는 다른 객체를 참조한다.
str3과 str4가 참조하는 객체의 값은 같다.
str1 hashcode: 985922955
str2 hashcode: 985922955
str3 hashcode: 586617651
str4 hashcode: 328638398
*/
메서드 영역에 생성된 같은 리터럴의 문자열 객체는 다시 생성되지 않는다. 즉 위 예제에서 str1과 str2는 같은 객체를 가리킨다(같은 참조 값을 갖는다).
== 비교연산자는 참조변수가 가진 참조값을 비교한다. 즉, 같은 객체를 가리키고 있다면 비교의 결과는 true이다(동일성 비교
). 같은 객체를 가리키고 있는지의 여부가 아니라 서로 가리키는 객체가 갖고 있는 값 자체가 같은 지를 알고싶은 거라면 public boolean equals(Object obj)
메서드를 사용한다(동등성 비교
).
System.identityHashCode()
는 객체의 고유한 hashcode를 리턴하는 메서드이다. hashcode는 객체를 식별하는 Integer 값으로, System.identityHashCode()
통해 리턴된 hashcode가 같다면 같은 객체이고, 다르면 서로 다른 객체이다.