스트링은 왜 불변(immutable)으로 설계되었을까?
기본적으로 자바에서는 String 객체의 값은 변경할 수 없다.
그렇다면 왜 String은 불변하게 만들었을까?
String이 불변인 이유는 크게 3가지로 볼 수 있다.
1. String 객체의 캐싱 기능과 성능
문자열 객체는 널리 사용되고 재사용될 가능성이 매우 높다. JAVA는 String 리터럴을 캐싱하고 재사용해 많은 힙공간을 절약할 수 있다. 예를 들어 아래같은 코드를 실행했을 때
ex 1)
String str1 = new String("hello");
String str2 = new String("hello");
메모리상에 2개의 인스턴스가 생성되게 된다. 하지만 리터럴 방식을 이용하면 Heap의 String pool이라는 공간에 String 을 저장해 실제로는 2개의 문자열 객체를 생성하는 것이 아닌 1개의 "hello" 라는 문자열을 pool안에 생성하고 이 문자열을 참조하도록 한다.
ex 2)
String s1 = "Cat";
String s2 = "Cat";
String s3 = new String("Cat");
2번째 예시에서도 보다시피 변수s2의 값이 새로 생성되는 것이 아닌 String pool에 이미 생성된 "Cat"을 참조하는 것을 볼 수 있다.
이 과정을 통해 메모리를 아낄 수 있어 특정 문자열 값을 재사용하는 빈도가 높을수록 성능 향상을 기대할 수 있다.
new 연산자로 생성하면 같은 내용이라도 여러 인스턴스가 heap영역에 생성된다.
2. 보안
JAVA에서는 아래와 같이 파라미터로 문자열을 넘길 경우가 자주 발생하는데
- DB연결을 위한 URL 패스워드 연결
- 네트워크 연결을 위한 host, port
- 이름, 나이 등등의 정보
String이 불변하지 않았다면 해커들의 악의적 공격에 의해 값이 변경되거나 잘못된 설계로 값이 변경된다면 어플리케이션에 심각한 보안적 취약점이 발생할 수 있다.
3. 안전성
String 객체는 변경할 수 없기 때문에, 여러 스레드에서 동시에 특정 String에 접근할 때 안정성을 보장할 수 있다.
또한 스레드가 값을 변경하는 작업을 실행한다 해도 값이 수정되는 것이 아닌 String pool에 새로운 문자열이 생성되기 때문에 Multi - Thread 환경에서도 안전하게 사용할 수 있다.
+ hashcode 캐싱
String 객체는 데이터 구조로 많이 사용되기 때문에 HashMap , HashTable , HashSet 등과 같은 해시 구현에서도 널리 사용됩니다 . hashCode () 메서드는 캐싱을 용이하게 하기 위해 String 클래스 에서 재정의 되어 첫 번째 hashCode() 호출 중에 해시가 계산 및 캐시되고 그 이후로 동일한 값이 반환됩니다. 이를 통해 컬렉션의 성능을 향상시킬 수 있다.
참고
'JAVA' 카테고리의 다른 글
[JAVA] 래퍼 클래스(Wrapper Class)란? (0) | 2024.05.31 |
---|---|
[JAVA] ENUM 이란? (0) | 2024.05.28 |
[JAVA] JVM(Java Virtual Machine) (0) | 2023.07.11 |
[JAVA]String, StringBuilder, StringBuffer (0) | 2023.04.08 |
[JAVA] 인터페이스 (0) | 2022.11.23 |