String,StringBuffer,StringBuilder

eden6187·2021년 8월 8일
0

Java

목록 보기
4/4
post-thumbnail

String은 Immutable하다.

String은 Immutable하기 때문에 한번 객체가 생성된 후에는 절대 변하지 않습니다.

public class Main {
    public static void addSuffix(String arg) {
        arg += "Suffix"; // 3,4
    }

    public static void main(String... args) {
        String prefix = new String("Prefix"); // 1
        addSuffix(prefix); // 2
        System.out.println(prefix);
    }
}

위의 코드를 보고 출력 결과 값으로 SuffixPrefix를 생각하셨다면 이 글은 당신을 위한 글입니다!!

String은 Immutable하다

Java를 공부하다가 한번쯤은 들어봤을 말입니다. Immutable 하다는 것은 일단 객체 자체가 한번 생성되면 절대 변하지 않는다는 말입니다.

위의 코드를 보게 되면

prefix 라는 변수에 담긴 String 객체의 참조 변수를 addSuffix 메소드 에 넘기게 되고,

addfix 메소드에서 arg 에 "Suffix"문자열을 추가합니다.

+= 이고.... Java에서 레퍼런스 타입은 Call-by-reference니까.. 굳이 반환은 안해줘도 되겠구나!

이런 생각이 들텐데요 String은 Immutable하기 때문에 실제로는 아래와 같은 과정을 거치게 되서 main() 메서드 에 prefix 변수는 그대로 "Prefix"로 유지 됩니다. 파란색으로 쓰여진 숫자가 위의 코드에 주석 처리된 부분의 숫자와 일치합니다.

빨간 상자로 표시된 부분을 보게 되면, arg 참조 변수는 실제로는 새로 생성된 인스턴스를 참조하고 있음을 알 수 있습니다! 🤯

String Object vs String Literal

"String은 immutable 객체입니다."

하지만, String 객체의 생성방식에 따라서 String형 레퍼런스 변수가 실제로 가리키는 인스턴스는 달라지게 됩니다.

이게 무슨 말일까요?

String str1 = new String("Hi");
String str2 = "Hi";
System.out.println(str1 == str2); // false!!

String 객체를 생성하는 방법에는 위와 같이 2가지 방식이 있죠! 하지만 str1이 참조하고 있는 객체와 str2가 참조하고 있는 객체는 다릅니다.

"String은 immutable 객체이고, String Constant Pool에 저장된다!"

이런말을 들어보셨다면 두 객체가 동일하다고 생각 하실 수 있습니다. 하지만, 두 객체가 같은지 확인해보면 실제로는 다른 것을 알 수 있습니다.

왜 그런것일까요?

위의 그림과 같이 생성되는 new를 사용하게 되면 String Pool에서 기존에 존재하는 객체를 가져오지 않고 새로운 객체를 생성하기 때문입니다.

String str1 = "Hi";
String str2 = "Hi";
System.out.println(str1 == str2); // true!!

그렇다면, 위의 코드에서 str1이 참조하는 str2가 참조하는 값은 같을까요? 네! 둘은 같은 객체를 참조합니다! 😄

new와는 달리 ""를 사용하여 String을 생성할 때에는 위와 같이 기존 String Pool에서 존재하는 객체가 있다면 해당 객체를 참조하기 때문입니다.

  • new를 통한 String 인스턴스를 Sting Object라 합니다. 이렇게 생성된 인스턴스는 스트링이 풀이 아닌 일반적인 힙 영역에 저장됩니다.
  • ""를 통해 생성한 String 인스턴스를 String Literal이라고 합니다.이렇게 생성된 인스턴스는 힙 영역 내부의 스트링 풀에 저장됩니다.

StringBuider

지금까지 살펴 본것과 같이 String 클래스는 + 연산을 할 때마다 새로운 객체를 생성하기 때문에

String a = "";
for (int len = 0; len < 10; len++){
    a += "Some Character";
}

위와 같이 + 를 남용하면 객체가 엄청나게 많이 생성되게 됩니다....🥵

그래서, 등장한 클래스가 StringBuilder인데요 String과 달리 StringBuider는 Immutable하지 않기 때문에

append() 를 통해서 concatination을 해주어도 새로운 객체가 생성되지 않습니다!

하지만, 동기화가 되지 않는다는 단점도 가지고 있습니다..!

StringBuffer

StringBuffer는 StringBuider와 같이 위에서 살펴본 String이 단점을 해결하고 + 동기화 문제까지 해결하기 위해 등장한 클래스 입니다.

정리

  • String : immutable하다. 따라서, + 연산을 하게 되면 새로운 객체를 반환한다.

  • StringBuilder : 따라서 연산을 해주어도 새로운 객체가 매번 생성되지 않는다. 하지만, 동기화 문제는 있다.

  • StringBuffer : StringBuilder의 장점 + 동기화 문제까지 해결해준다.

지금까지 짧게 String과 StringBuilder StringBuffer에 대하여 설명 드렸습니다!
잘못된 내용이나 추가하면 좋겠을 것 같은 내용이 있다면 댓글 주시기 바랍니다!

출처

String object vs literal

final vs immutable

0개의 댓글

관련 채용 정보