peaches-book-study / effective-java

이펙티브 자바 3/E
0 stars 2 forks source link

Item 63. 문자열 연결은 느리니 주의하라 #66

Open pyeong114 opened 2 months ago

pyeong114 commented 2 months ago

Chapter : 9. 일반적인 프로그래밍 원칙

Item : 63. 문자열 연결은 느리니 주의하라

Assignee : pyeong114


🍑 서론

🍑 본론

문자열 연결 연산자+는 여러 문자열을 하나로 합쳐주는 편리한 수단이다.

한 줄짜리 출력값 혹은 작고 크기가 고정된 객체의 문자열 표현을 만들 때라면 괜찮지만, 본격적으로 사용하기 시작하면 성능 저하를 감내하기 어렵다

문자열 연결 연산자로 문자열 n개를 잇는 시간은 n 제곱에 비례한다.

문자열은 불변이라서 두 문자열을 연결할 경우 양쪽의 내용을 모두 복사해야 하므로 성능 저하는 피할 수 없는 결과다.

public String statement(){
    String result = "";
    for(int i = 0; i < numItems(); i++)
        result += lineForItem(i); // 문자열 연결
    return result;
}

품목이 많으면 심각하게 느려질 수 있다. 성능을 포기하고 싶지 않다면 String 대신 StringBuilder를 사용하자

public String statement2(){
    StringBuilder b = new StringBuilder(numItems() * LINE_WIDTH);
    for(int i = 0; i < numItems(); i++)
        b.append(lineForItem(i));
    return b.toString();
}

🍑 결론

성능에 신경 써야 한다면 많은 문자열을 연결할 때는 문자열 연결 연산자(+)를 피해라 대신 StringBuilder의 append 메서드를 사용하라


Referenced by

-

pyeong114 commented 2 months ago

문자열 연결 과정:

만약 s1 + s2와 같이 두 개의 문자열을 연결하면, 새로운 문자열 객체가 생성되고, s1의 모든 문자와 s2의 모든 문자가 이 새로운 객체로 복사됩니다. 예를 들어, s1이 10자 길이이고 s2가 5자 길이라면, 새로운 문자열 객체를 생성하고 15자를 복사해야 합니다. 여러 문자열을 연결할 때:

만약 n개의 문자열을 연결하는 경우, 이를 반복적으로 수행해야 합니다. 예를 들어, 세 문자열 s1 + s2 + s3를 연결한다고 가정하면, 다음과 같은 단계가 일어납니다: s1 + s2를 수행하여 새로운 문자열 temp1을 만듭니다. 이때, temp1의 길이는 s1.length() + s2.length()입니다. temp1과 s3를 연결하여 최종 문자열을 만듭니다. 이때, 최종 문자열의 길이는 temp1.length() + s3.length()입니다. 시간 복잡도 분석:

첫 번째 단계에서, s1과 s2를 연결하는 데 걸리는 시간은 O(len(s1) + len(s2))입니다. 두 번째 단계에서, temp1과 s3를 연결하는 데 걸리는 시간은 O(len(temp1) + len(s3))입니다. 이런 식으로 n개의 문자열을 연결하면 각 단계마다 이전까지의 모든 문자열 길이를 더한 만큼의 시간을 소비하게 됩니다. 따라서, n번째 문자열을 연결할 때는 O(len(s1) + len(s2) + ... + len(sn))의 시간이 걸리게 됩니다. 이 과정을 반복하면, 전체 시간 복잡도는 𝑂(𝑛2) O(n 2)이 됩니다. 이를 더 효율적으로 처리하기 위해서는 StringBuilder를 사용하는 것이 좋습니다. StringBuilder는 내부적으로 가변적인 버퍼를 사용하여 문자열을 더하고, 최종적으로 한 번의 복사로 문자열을 생성하기 때문에 시간 복잡도가 𝑂(𝑛) O(n)에 가깝습니다.

Lainlnya commented 2 months ago

abc + de + f

"" < abc + de -> abcde "" < abcde + f -> abcdef