ABOUT ME

작은 디테일에 집착하는 개발자

Today
-
Yesterday
-
Total
-
  • [Java] String, StringBuffer, StringBuilder
    IT Study/컴퓨터 기초 2023. 3. 26. 15:40
    728x90

    오늘은 자바에서 문자열을 다루는 클래스인 String, StringBuffer, StringBuilder에 대해 함께 알아보도록 하겠습니다.

     

    1. String이란?

    Java에서 문자열을 다루는 클래스로, 불변(immutable)이라는 특징을 가져 한 번 생성된 문자열은 변경할 수 없습니다.

     

    1-1. String 특징

    문자열을 저장할 때 문자 배열 char[]을 사용합니다. 따라서 인덱스를 사용해, 각 문자열의 문자에 접근이 가능합니다.

     

    1-2. String 예시

    String 클래스에서 주로 사용되는 변수나 메서드를 아래 예시에 작성해뒀습니다.

    import java.util.Arrays;
    
    public class Main {
        public static void main(String[] args) {
            // String 객체 생성 방법
            String str1 = "Hello";  // 리터럴 방식
            String str2 = new String("World");  // 생성자 방식
    
            // 문자열 비교
            boolean isEqual = str1.equals(str2);  // equals 메서드 사용
            System.out.println("str1과 str2는 같은 문자열인가? " + isEqual);
    
            // 문자열 연결
            String str3 = str1 + " " + str2;  // + 연산자 사용
            System.out.println("연결된 문자열: " + str3);
            
            // 문자열 길이
            int length = str3.length();
            System.out.println("str3의 길이: " + length);
    
            // 문자열 추출
            String subStr = str3.substring(6);
            System.out.println("추출된 문자열: " + subStr);
            
            // 문자열 치환
            String replacedStr = str3.replace("World", "Java");
            System.out.println("치환된 문자열: " + replacedStr);
    
            // 문자열 분리
            String[] splitStr = str3.split(" ");
            System.out.println("분리된 문자열: " + Arrays.toString(splitStr));
            
            // 문자 추출
            char ch = str3.charAt(6);
            System.out.println("추출된 문자 : " + ch);
            
            // 문자열 찾기
            int index = str3.indexOf('W');
            System.out.println("문자 W의 인덱스 번호 : " + index);
            
            // 문자열 포함 여부
            boolean contains = str3.contains("llo");
            System.out.println("str3에 \"llo\" 포함되었는가? " + contains);
            
            // 앞뒤 공백 제거
            String str4 = " Bye Java ";
            String trimStr = str4.trim();
            System.out.println("앞뒤 공백 제거 : " + trimStr);
            
            // 모든 타입 -> String 변환
            int num = 100;
            String strNum = String.valueOf(num);
            System.out.println("num -> str : " + strNum);
        }
    }
    <출력>
    str1과 str2는 같은 문자열인가? false
    연결된 문자열: Hello World
    str3의 길이: 11
    추출된 문자열: World
    치환된 문자열: Hello Java
    분리된 문자열: [Hello, World]
    추출된 문자 : W
    문자 W의 인덱스 번호 : 6
    str3에 "llo" 포함되었는가? true
    앞뒤 공백 제거 : Bye Java
    num -> str : 100

     

    문자열
    비교
    문자열
    연결
    문자열
    길이
    문자열
    추출
    문자
    추출
    문자열
    분리
    문자열
    치환
    문자열
    포함 여부
    앞뒤 공백
    제거
    String
    으로 변환
    equals +, concat length substring charAt split replace contains trim valueOf

     

    1-2-1. valueOf()

    valueOf 메서드는 기본 자료형이나 객체를 문자열로 변환합니다.

    valueOf 메서드는 여러 자료형에 오버로딩 되어 있어, 해당 자료형의 값을 받아 해당 자료형을 문자열로 변환해 반환합니다.

    int num = 10;
    String str1 = String.valueOf(num); // "10"
    
    double d = 3.14;
    String str2 = String.valueOf(d); // "3.14"
    
    char[] char = {'a', 'b', 'c'};
    String str3 = String.valueOf(char); // "abc"
    
    boolean bool = true;
    String str4 = String.valueOf(bool); // "true"

     

    이 챕터에서 주목해야 할 것은 String.valueOf(char)와 String.valueOf(char[]) 입니다.

     

    char 배열을 생성하고,

    1. 배열 전체를 문자열로 변환하는 것2. 각 요소를 문자열로 변환한 뒤 배열에 저장하는 예시도 함께 보도록 하겠습니다.

    public class Main {
    	public static void main(String[] args) {
    		char[] cArr = {'J', 'a', 'v', 'a'};
    		
    		// 1. 문자열로 변환
    		String str = String.valueOf(cArr);
    		System.out.println(str);
    		
    		// 2. 각 요소를 문자열로 변환한 뒤 배열에 저장
    		String[] strArr = new String[cArr.length];
    		for (int i = 0; i < cArr.length; i++) {
    		    strArr[i] = String.valueOf(cArr[i]);
    		}
    		System.out.println(Arrays.toString(strArr));
    	}
    }
    <출력 결과>
    Java
    [J, a, v, a]

     

    1-2-2. reverse()

    String 클래스에는 reverse() 메서드가 존재하지 않습니다.

    그러나 아래 StringBuffer나 StringBuilder 클래스의 reverse() 메서드를 활용하여 문자열을 역순으로 출력할 수 있습니다.

    아래의 예시를 통해 자세히 알아보도록 하겠습니다.

    String str = "hello";
    String reversedStr = new StringBuilder(str).reverse().toString();
    System.out.println(reversedStr); // "olleh" 출력

     

    위의 예시에서는reversedStr이라는 String 객체를 선언하고,

    StringBuilder 객체 생성과 동시에 reverse() 메서드로 문자열을 뒤집어

    toString()을 통해 다시 String 객체로 변환하여 반환합니다.

    이와 같이 StringBuffer/StringBuilder 클래스의 reverse()를 활용하여 String도 역순 출력할 수 있다는 것을 기억하면 좋을 것 같습니다.

     

    2. StringBuffer란?

    가변적인 문자열을 처리하기 위한 클래스로, 문자열을 수정할 수 있습니다.

     

    2-1. StringBuffer 특징

    StringBuffer는 동기화를 보장하기 때문에 멀티스레드 환경에서 안전하게 사용할 수 있습니다.

    더불어 String은 문자열을 수정하기 위해 새로운 객체를 생성해야 했지만,

    StringBuffer는 기존 객체 내에서 문자열을 수정할 수 있습니다. (String 클래스보다 메모리 사용이 효율적!)

    그러나 문자열을 수정할 때마다 내부 버퍼를 재할당하기 때문에 성능 저하의 우려가 있습니다.

     

    2-2. StringBuffer 예시

    public class Main {
        public static void main(String[] args) {
            // StringBuffer 객체 생성
            StringBuffer sb = new StringBuffer("Hello");
    
            // append() 메서드로 문자열 추가
            sb.append(" World!");
            System.out.println(sb.toString());
    
            // delete() 메서드로 문자열 삭제
            sb.delete(5, 11);
            System.out.println(sb.toString());
    
            // insert() 메서드로 문자열 삽입
            sb.insert(5, " World");
            System.out.println(sb.toString());
    
            // replace() 메서드로 문자열 교체
            sb.replace(6, 11, "there");
            System.out.println(sb.toString());
    
            // reverse() 메서드로 문자열 뒤집기
            sb.reverse();
            System.out.println(sb.toString());
        }
    }
    <출력>
    Hello World!
    Hello!
    Hello World!
    Hello there!
    !ereht olleH

     

    문자열 추가
    (인스턴스의 끝)
    문자열 추가
    (원하는 위치)
    문자열
    삭제
    문자열 역순 문자열 추출 문자 추출 문자열 위치
    추출
    append insert delete reverse substring charAt indexOf

     

    2-2-1. capacity()

    현재 StringBuffer 객체의 *용량(capacity) 반환합니다. (*용량 : StringBuffer 객체에 문자열을 추가할 수 있는 최대 길이)

    StringBuffer sb1 = new StringBuffer();
    System.out.println(sb1.capacity());
    
    StringBuffer sb2 = new StringBuffer("Hello");
    System.out.println(sb2.capacity());
    <출력>
    16
    21

     

    2-2-2. ensureCapacity

    객체의 용량을 증가시킬 때 사용하는 메서드입니다. 지정해준 값 이상으로 증가시킵니다.

    StringBuffer sb = new StringBuffer();
    System.out.println(sb.capacity());
        	
    sb.ensureCapacity(30);
     System.out.println(sb.capacity());
    <출력>
    16
    34

     

    30으로 지정했으나, 지정된 값 이상으로 증가하는 것을 확인할 수 있습니다.

    용량이 증가하는 시점과 얼마나 증가하는지는 실제 버퍼를 사용할 때 중요한 요소 중 하나지만,

    이 부분은 StringBuffer 클래스에서 자체적으로 관리하고 있기 때문에 사용자가 직접 조절할 수는 없습니다.

    미리 정해진 알고리즘에 따라 동작한다는 것만 알고 계시면 좋을 듯합니다.

     

    2-2-3. setLength

    용량이 아닌 길이(문자열의 길이)를 지정된 값으로 설정합니다.

    만약 StringBuffer 객체의 현재 길이가 지정된 값보다 작다면, 뒤에 공백을 추가하여 지정된 길이로 설정합니다.

    StringBuffer sb1 = new StringBuffer("Hello Java");
    sb1.setLength(15);
        	
    String str1 = sb1.toString();
    System.out.println(str1);
    <출력>
    Hello Java     (Hello Java\0\0\0\0\0)

     

    만약 StringBuffer 객체의 현재 길이가 지정된 값보다 크다면, 지정된 길이까지만 잘라냅니다.

    StringBuffer sb2 = new StringBuffer("Hello Java");
    sb2.setLength(5);
        	
    String str2 = sb2.toString();
    System.out.println(str2);
    <출력>
    Hello

     

    3. StringBuilder란?

    StringBuffer와 같이 문자열 수정이 가능한 클래스입니다.

    StringBuilder는 Java5부터 도입되어 Java9에서는 개선된 기능을 제공하고 있습니다.

     

    3-1. StringBuilder 특징

    StringBuffer와 달리 동기화를 제공하지 않아 멀티스레드 환경에서 안전하지 않습니다.

    (단일 스레드 환경에서는 StringBuffer보다 빠름!)

    그러나 문자열을 동적으로 생성하고, 조작하거나 연산이 많은 경우에는 성능 향상을 위해 사용합니다.

     

    3-2. StringBuilder 예시

    위 2-3의 StringBuffer의 내용을 참고하세요!

     

    그럼 StringBuilder - StringBuffer 언제 누굴 사용해야 하나요? 

    단일 스레드 환경에서 문자열 처리를 할 때는 (동기화를 보장하지 않는) StringBuilder를,

    멀티 스레드 환경에서 문자열 처리를 할 때는 (*동기화를 보장하는) StringBuffer를 사용하는 것이 좋습니다.

    *동기화 : 여러 스레드가 공유하는 자원에 대한 접근을 조율하는 것

    (예 : 다수의 스레드가 StringBuffer의 append() 메서드를 호출하더라도, 각 스레드는 순차적으로 접근하고 변경할 수 있도록 보호합니다.)

Designed by Tistory.