포스트

20. String 클래스

String 클래스와 new 인스턴스에 대해 알아가보자.

20. String 클래스

String

문자열을 다루는 자바 내장 클래스

  • String은 new~ 로 만들어지느냐 “” 문자열 리터럴로 만들어지느냐에 따라 다르게 동작된다. 확인해보자.

new~

Heap에 새롭게 생성하는 모든 String 인스턴스는 동일한 내용을 가지고 있어도 다른 객체이다.

1
2
3
String s1;                        // JVM Stack
s1 = new String("Hello");         // Heap
String s2 = new String("Hello");  // JVM Stack -> Heap

new 와 Heap

문자열 리터럴

String 상수 풀에 인스턴스를 생성하고 만약 같은 문자열의 인스턴스가 있다면 중복되게 만들지않는다

1
2
3
String s1;
s1 = "Hello";
String s2 = "Hello";

문자열 리터럴

intern( )

인스턴스를 String pool에 생성한다. 상수 풀에 동일한 문자열이 있다면 기존 것을 사용한다.

1
2
3
String s1 = new String("Hello"); // Heap에 인스턴스 생성
String s2 = s1.intern();         // String pool에 인스턴스 새로 생성
String s3 = "Hello";             // String pool에 s2에서 만든 "Hello" 문자열 존재로 해당 인스턴스 부여

intern

다형적 변수와 형변환

1
2
3
4
5
Object obj = new String("test");
obj.메서드 // -----------------> Object의 메서드 사용 가능. but String 메서드는 사용 불가능
String s = (String) obj; // -> Object를 강제 형변환.
s.메서드 // -------------------> String의 메서드 사용가능
((String)obj); // -----------> 한번만 사용한다면 이렇게도 사용 가능하다.

다형적 변수

new String(byte 배열)

1
2
3
4
5
byte[] bytes =
        {(byte) 0xb0, (byte) 0xa1, (byte) 0xb0, (byte) 0xa2, 0x30, 0x31, 0x32, 0x41, 0x42, 0x43};
    // 문자 코드 값이 저장된 바이트 배열로 String 인스턴스 생성
    String s4 = new String(bytes);
    System.out.printf("s4=%s\n", s4);

배열 new String

byte 배열을 String에 넣었을 때 » 출력 시 글씨가 깨져 노출된다

why?
JVM이 해당 코드를 변환할때는 file.encoding(JVM 프로퍼티)에 따라 인식 후 UTF 16BE 변환하여 String 인스턴스를 생성하게 되는데..
Eclipse IDE는 클래스를 실행할 때 -D file.encodeing = UTF-8로 JVM 프로퍼티를 설정하게된다.
결국 byte 배열 값을 UTF-8 문자 코드라고 가정을 하고 변환하기 때문에 맞지않는 한국어는 깨져 노출된다.

wrapper 클래스

  • primitive data type에 대응하여 만든 클래스를 primitive data를 포장하는 객체라고 해서 wrapper 클래스로 불림
wrapper 클래스 종류
  1. Byte > byte
  2. Short > short
  3. Integer > int
  4. Long > long
  5. Float > float
  6. Double > double
  7. Boolean > boolean
  8. Character > char
1
2
3
int i = 100;                       // 그냥 값 100
Integer obj = Integer.valueOf(i);  // Integer라는 클래스에 100이라는 값을 가진 객체.
int i2 = obj.intValue();           // 그냥 값 100

primitive data type 값을 wrapper 클래스에 넣는 걸 boxing 이라하고
wrapper 클래스에서 값을 빼와 primitive data화 시키는걸 unboxing이라고 한다.
이런 작업이 귀찮고 불편한데…. 이를 자바에서 auto로 지원해준다. 오토박싱, 오토 언박싱이라고 한다.

1
2
Integer obj = 100; // ==> Integer.valueOf(100) autoBoxing 수행
int i = obj;       // ==> obj.inValue() autoUnboxing 수행 

대신 이를 수행하는건 JVM이 아닌 컴파일러에서 수행한다.

wrapper

미니 프로젝트(myapp)

배열 크기를 자동으로 증가 시키자

배열은 메모리 크기가 고정이 되고 변경 할 수 없다.
그렇다면.. 그 이상의 값을 보관해야될 때는 어떻게 해야하는가…..?
간단하다. 기존 배열보다 큰 배열을 만들어 주고 값을 복사해서 넣으면 된다. (직접해보자)

LinkedList 자료구조

  1. 배열 방식
    1. 장점 : 메모리 크기 고정됨
    2. 단점 :
      1. 메모리 크기를 늘릴 수 없다. → 늘리기 위해서 새 배열 생성 후 기존 값 복사해야함 → 가비지 다량 발생.
      2. 삽입, 삭제 시 항목의 값을 밀고 당겨야하기 때문에 실행 속도가 떨어짐
  2. Linked List 방식
    1. 장점 :
      1. 메모리를 늘리기 쉽다
      2. 삽입, 삭제가 쉽다
    2. 단점 : 데이터 조회 시 시간이 많이 소요된다.

→ 배열의 단점들을 보완하기 위해 myapp에서 Linked List 방식으로 데이터를 저장할 예정

LinkedList 구동 원리

  1. 입력 입력

  2. 조회 조회

  3. 삭제

    1. 첫번째 노드를 삭제할 때 삭제 첫번째

    2. 중간 노드를 삭제할 때 삭제 중간

    3. 마지막 노드를 삭제할 때 삭제 마지막

상속의 한계

  • 상속을 받을 클래스 안의 메서드들 네이밍이 모두 다르다면…. 상속

상속을 받은 모든 클래스들을 고쳐야하는 상황이 올지도 모른다. 이를 보완하기 위해 인터페이스를 사용한다. 인터페이스는 다음 글에서 상술할 예정이다.

이 기사는 저작권자의 CC BY 4.0 라이센스를 따릅니다.