# 이 클래스들은 모두 문자열을 저장하고 관리하는 클래스이다.

1) String

String 클래스와 StringBuilder, StringBuilder 클래스의 차이점은 String은 불변하고(immutable), StringBuffer는 가변하다는(mutable) 점이다.

 

String 객체는 new 연산을 통해 생성되면 할당된 메모리 공간이 변하지 않는다. 따라서 + 연산자 또는 concat같은 메소드를 통해 기존에 생성한 String 객체에 다른 문자열을 추가해도 기존 문자열에 새로운 문자열을 붙이는 것이 아닌 새로운 String 객체를 new로 생성하여 새로운 메모리 공간을 할당받아 연결된 문자열을 저장한다.

 

즉 String 클래스 객체는 Heap 메모리 영역(가비지 컬렉션이 동작하는 영역)에 생성하여 한번 생성된 객체의 내용을 변화시킬 수 없다. 따라서 많은 연산을 수행하면 계속하여 객체를 만드는 오버헤드가 발생하므로 성능이 떨어진다는 단점이 있다. 하지만 객체가 불변하기 때문에 단순하게 읽는 연산에서는 다른 클래스보다 빠르게 읽을 수 있다는 장점이 있다.(불변하기에 멀티스레드 환경에서 동기화 신경쓸 필요가 없다)

 

2) StringBuilder, StringBuffer

StringBuilder와 StringBuffer는 가변적이다. 즉 문자열 연산에 있어서 클래스를 한번만 만들고(new), 연산이 필요할 때 크기를 변경시켜서 문자열을 변경한다. 따라서 문자열 연산이 많을 때 사용하면 좋다.

 

StringBuilder,StringBuffer클래스는 String클래스와 다르게 동작한다. 만약 문자열 연산 등으로 기존 객체의 공간이 부족하게 되는 경우, 기존의 버퍼 크기를 늘리며 유연하게 동작한다. 그리고 StringBuilder와 StringBuffer 클래스가 제공하는 메서드는 서로 동일하다. 

 

그렇다면 두 클래스 간의 차이점은 무엇일까. 차이점은 StringBuffer는 멀티쓰레드환경에서 synchronized키워드가 가능하므로 동기화가 가능하다. 즉, 동기화의 차이이다. 따라서 StringBuffer는 thread-safe하다. StringBuilder는 동기화를 지원하지 않기 때문에 멀티쓰레드환경에서는 적합하지 않다. 대신 StringBuilder가 동기화를 고려하지 않기 때문에 싱글쓰레드 환경에서 StringBuffer에 비해 연산처리가 빠르다.

 

 

**정리하자면 

String클래스는 불변 객체이기 때문에 문자열 연산이 많은 프로그래밍이 필요할 때 계속해서 인스턴스를 생성하므로 성능이 떨어지지만 짧은 문자열을 더할 경우, 조회가 많은 환경, 멀티쓰레드 환경에서 성능적으로 유리하다.

StringBuffer클래스와 StringBuilder클래스는 문자열 연산이 자주 발생할 때 문자열을 추가하기 위한 append() 메서드에 대해서 StringBuffer는 String 보다 월등한 성능을 가지고 있고, 문자열이 변경가능한 객체기 때문에 성능적으로 유리하다.

StringBuffer와 StringBuilder의 차이점은 동기화지원의 유무이고 스레드에 안전한지 여부 관계를 따지지 않는, 동기화를 고려하지 않는 환경에서 StringBuilder가 성능이 더 좋고, 스레드에 안전한 프로그램이 필요한 때, 개발 중인 시스템의 부분이 스레드에 안전한지 모를 경우, 즉 동기화가 필요한 멀티쓰레드 환경에서는 StringBuffer를 사용하는 것이 유리하다.

 

문자열을 추가하기 위한 append() 메서드에 대해서 StringBuffer는 String 보다 월등한 성능을 보인다. 하지만 toString()메서드에 대해서는 오히려 String객체 생성을 하는 내부적인 처리 때문에, StringBuffer가 String 보다 더 많은 자원을 소모한다.

 

그에 비하여, String 클래스는 StringBuffer 와 비교하여 인스턴스화를 통하여 객체를 생성할 때 상대적으로 적은 자원을 소모하며, toString() 메서드를 통하여 String 객체로 바꿀 필요가 없다. 이 때문에 StringBuffer 는 하나의 문자열에 대하여 다른 문자나 문자열 추가가 여러 번 행해지는 곳에서 유리하며, 단 한번의 문자열 추가에 대해서는 StringBuffer를 사용하는 것은 오히려 독이다. 

 

 

**간단요약**

1. 읽기용 & 공유용도 문자열을 사용 => String

 

2. 문자열 수정 & 멀티 스레드 환경 => StringBuffer

 

3. 문자열 수정 & 싱글 스레드 환경 => StringBuffer

 

 

 

'Java' 카테고리의 다른 글

#자바_Comparable, Comparator  (0) 2020.01.13

자바 프로그래밍을 하다보면 객체를 정렬해야 할 경우가 자주 있다.

ex) 학생들을 국어 점수를 감소하는 순, 좌표를 x좌표가 증가하는 순 등..

 

객체의 정렬 기준을 명시하는 방법에는 두 가지가 있다.

1. Interface Comparable

2. Interface Comparator

 

 

 

1. Comparable 

정렬 수행 시 기본적으로 적용되는 정렬 기준이 되는 메서드를 정의하는 인터페이스

 

> 구현 방법

정렬할 객체에 Comparable interface를 implements 후, compareTo() 메서드를 오버라이드하여 구현한다.


compareTo() 메서드 작성법 - 리턴 값이 0이나 음수면 기준값은 고정, 양수 값이면 바뀐다.

  1. 현재 객체 < 파라미터로 넘어온 객체: 음수 리턴

  2. 현재 객체 == 파라미터로 넘어온 객체: 0 리턴

  3. 현재 객체 > 파라미터로 넘어온 객체: 양수 리턴

 

 

Comparable Example


import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

public class compa {
	public static void main(String[] args) {
		int x = 3, y = 4;
		List arrList = new ArrayList<>();
		arrList.add(new Point(x, y));
		x=1; y=1;
		arrList.add(new Point(x, y));
		Collections.sort(arrList);
		x=4; y= 7;
		arrList.add(new Point(x, y));
		for(int i=0; i<arrList.size(); i++) {
			System.out.println(arrList.get(i).x +" "+arrList.get(i).y);
		}
	}
	// x좌표가 증가하는 순, x좌표가 같으면 y좌표가 감소하는 순으로 정렬하라.
	static class Point implements Comparable {
	    int x, y;
	    
	    public Point(int x,int y) {
	    		this.x=x;
	    		this.y=y;
	    }
	    @Override
	    public int compareTo(Point p) {
	        if(this.x > p.x) {
	            return 1; // x에 대해서는 오름차순
	        }
	        else if(this.x == p.x) { // 같을경우에
	            if(this.y < p.y) { // y에 대해서는 내림차순
	                return 1;
	            }
	        }
	        return -1;
	    }
	}

}

 

 

2. Comparator

정렬 가능한 클래스(Comparable 인터페이스를 구현한 클래스)들의 기본 정렬 기준과 다르게 정렬 하고 싶을 때 사용하는 인터페이스

 

compare() 메서드 작성법 - 리턴 값이 0이나 음수면 기준값은 고정, 양수 값이면 바뀐다.

  1. 현재 객체 < 파라미터로 넘어온 객체: 음수 리턴

  2. 현재 객체 == 파라미터로 넘어온 객체: 0 리턴

  3. 현재 객체 > 파라미터로 넘어온 객체: 양수 리턴

Comparator Example


 	public static void main(String[] args) throws NumberFormatException, IOException {
		BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
		int N = Integer.parseInt(br.readLine());
		ArrayList arrList = new ArrayList<>();
		StringTokenizer st;
		for(int i=0; i tmp = new ArrayList<>();
        ....
        Collections.sort(tmp, new point_compartor());
	}
	public static class Point implements Comparable{
		int x;
		int y;
		public Point(int x,int y) {
			this.x=x;
			this.y=y;
		}
		@Override
		public int compareTo(Point o) {
			int val = this.x - o.x;
			if(val == 0) {
				return this.y-o.y;
			}else
				return val;
		}
	}
	
	public static class point_compartor implements Comparator{

		@Override
		public int compare(Point o1, Point o2) {
			// TODO Auto-generated method stub
			return o1.y-o2.y;
		}
	}
    
   

+ Recent posts