God of Java #2

5 minute read

God of Java #2

1. API

API : Application Programming Interface

많은 클래스를 사용할 때 참조하는 문서.

Deprecated

문제를 야기시키거나 혼동을 가져오거나 더이상 사용가치가 없을 때 호환성을 유지하기 위하여 사용.

Deprecated된 메소드나 생성자는 사용하지 않는 것이 좋음.

2. String

클래스 중에더 유일하게 더하기 연산을 제공하는 클래스.

public final class String extends Object implements Serializeable, Comparable<String>, CharSequence
  • final class이기 때문에 상속이 불가한 클래스
  • 모든 클래스의 부모 클래스는 Object클래스 이므로 이외의 별도로 확장한 클래스는 없음.
  • Serializeable : 객체를 파일로 저장하거나 다른 서버에 전송이 가능하도록 함. 구현해야 하는 메소드가 하나도 없는 인터페이스.
  • Comparable : 객체의 값을 비교가 가능하게 만듬. compareTo() 메소드가 존재.
  • CharSequence: 문자열을 다루기 위한 클래스를 명시적으로 나타냄.
캐릭터 셋
  • ISO-8859-1 : ISO 라틴 알파벳
  • UTF-8 : 8비트 UCS 변환 포맷
  • MS949: MS에서 만든 한글 확장 완성형 인코딩

잘못된 캐릭터 셋으로 변환을 하면 알 수 없는 문자로 변환이 되기도 함으로, 캐릭터 셋을 잘 지정하고 변환할 것.

NULL Check

어떤 참조 자료형도 null이 될 수 있음.

객체가 널이라는 말은 아무런 초기화가 되어있지 않으며, 클래스에 선언되어 있는 어떤 메소드도 사용이 불가한 상태.

String Method

length() : 문자열의 길이를 확인.

isEmpty() : 문자열이 비어있는지 확인.

equals(): 문자열이 같은지 비교.

contains() : 문자열을 포함하고 있는지 확인.

startwith() / endswith(): 문자열이 특정 문자열로 시작하거나 끝나는지 확인.

substring() : 문자열을 자르기 위함. 시작할 인덱스와 자를 범위의 인덱스를 매개변수로 전달.

split(): 문자열을 특정 캐릭터나 정규표현식으로 나눔.

concat(): 문자열을 합침.

trim(): 문자열의 좌/우 공백을 제거함.

replace() / replaceAll(): 문자열을 대체함.

format(): %s-문자열, %d-정수형, %f-소숫점이 있는 수, %%-%

String test = "안녕하세요. 저는 %s이며, %d살 입니다."
System.out.println(String.format(test, "Wooni", 20));

valueOf(): 기본 자료형을 문자열로 변환하는 메소드. String으로 변환만하고 문자열을 합치는 과정을 하지 않을 경우 권장. 참조 자료형의 경우 NullPointerException이 발생할 수 있기때문에 toString()보다 valueOf()의 사용을 권장.

Integer test = 0;
System.out.println(String.valueOf(test)); // 0
System.out.println(String.valueOf(null)); // null

String test2 = null;
test2.toString() // occur Null Pointer Exception.

intern(): 절대 사용하지 말아야할 메소드. pool에 재사용이 가능한 객체가 있는지 확인하고, 해당 객체가 있으면 그 객체의 주소 값을 리턴함. 즉 같은 값을 가지는 객체는 같은 주소값을 가질 수 있도록 하는 메소드.

  • Regular Expression : 이메일을 점검하거나 URL을 점검하는 등의 특정 문자의 포맷을 공식에 따라 만든 식.
  • 정규표현식으로 문자열을 나누려면 split을, 특정 문자열로 나누려면 StringTokenizer를 사용하는 것이 좋음.
StringBuffer and StringBuilder

String의 더하기 연산을 해야하는 경우 한 String변수의 값을 더하면 이전 값을 사용할 수 없어짐.

StringBuffer는 Thread Safe하지만 StringBuilder는 ThreadSafe하지 않음.

StringBuilder 하나의 메소드 내에서 문자열을 생성하여 더할 경우. StringBuffer는 어떤 클래스 변수로 문자열을 더하기 위한 문자열이 선언되어있고, 여러 쓰레드에서 이 변수를 동시에 접근해야 하는 경우.

두 클래스 모두 문자열을 다루기때문에 CharSequence 인터페이스를 구현했음.

3. Java.lang

Java.lang은 별도의 import를 하지 않고도 사용할 수 있음.

OOM(Out Of Memory) vs StackOverflowError

OOM: 메모리가 부족하여 발생.

StackOverflow: 호출된 메소드가 너무 많을때.

Java에서 스택은 메소드의 호출 순서나 메소드내의 변수들의 대한 정보를 관리하고 실제 Heap에 객체를 가지는 주소 값을 참조하고 있음.

기본 자료형은 Heap이 아닌 Stack에 저장되어 관리.

Number를 확장하는 기본 자료형의 Wrapper Class

자바 컴파일러에서 자동으로 형변환을 하기 때문에 겉보기로는 참조 자료형이지만 기본자료형처럼 사용 가능.

Character를 제외하고 문자열 값을 기본 자료형으로 리턴하는 parse()와 참조자료형으로 리턴하는 valueOf()라는 static 메소드를 제공함.

각 Wrapper Class는 클래스 변수로 Min과 Max값을 가지고 있음.

돈계산과 같이 중요한 계산을 하는 경우에는 BigInteger나 BigDecimal을 사용해야 정확한 계산이 가능.

각종 정보를 확인하기 위한 System Class

System에는 3개의 클래스 변수가 선언되어 있음.

  • static PrintStream err : 에러 및 오류 출력

  • static InputStream in: 입력 값을 처리

  • static PrintStream out: 출력 값을 처리.

    /* 
       System : class이름
       out: System class내 static변수
       println(): PrintStream 클래스에서 출력을 위해 제공하는 static 메소드.
    */
    System.out.println();
    
절대 사용하지 말아야할 System클래스의 메소드
  • gc() : gc()를 명시적으로 호출.
  • runFinalization(): Object에 선언되어있는 finalize()메소드를 호출하는 메소드.

-> JVM에서 보통 자신의 참조하는 객체가 없으면 자동으로 수행되기 때문에 개발자가 명시적으로 호출할 필요가 없음.

  • exit() : 어플리케이션을 강제로 종료하는 메소드.
System Class내의 currentTimeMillis() vs nanoTime()

currentTimeMillis()는 현재 시간을 나타날때 사용.

nanoTime()은 시간의 차이를 계산할 때 사용.

Java.lang의 Math와 StrictMath

Math는 시스템의 따라 결과가 달라질 수 있지만 StrictMath는 환경에 상관없이 동일한 값을 리턴.

Math는 대부분 StrictMath클래스의 메소드를 호출하도록 되어있고, StrictMath는 Native로 선언되어 있음.

4. 실수를 방지하기 위한 Generic.

Junit

메소드나 클래스 같은 작은 단위 테스를 쉽게할 수 있는 프레임 워크.

Generic은 사전에 형변환의 문제점을 방지하기 위함.

여기서 사전이라는 의미는 실행시 예외가 발생하는 것이 아니라, 컴파일 시에 점검할 수 있도록 하는 것.

<>안에는 현존하는 클래스를 사용해도 되고, 존재하지 않는 클래스를 사용해도 됨. 즉 가상의 타입 이름이라고 생각하면 됨.

public class GenericTest<T> implements Serializeable{
  private T testObject;
  public void setObject(T testObject){
    this.testObject = testObject;
  }
  public T getObject(){
    return this.testObject;
  }
}

public static void main(String[] args){
  GenericTest<String> test = new GenericTest<String>();
  test.setObject("abc");
  System.out.println(test.getObject());	/// "abc"
}
  • E: 요소
  • K: 키
  • N: 숫자
  • T: 타입
  • V: 값
  • S,U,V: 2,3,4번째 선언된 타입.
Generic의 ?는 뭐지

whilecard라고 부르며, 어떤 타입이 제네릭 타입이 되더라도 상관 없을 때.

?로 명시적 타입을 받은것이 아니기 때문에 받은 값은 Object로만 처리해야함.

어떤 객체는 wildcard로 선언하고, 그 객체의 값을 가져올 수는 있지만 타입으로 값을 지정하는것은 불가능.

상속이 된 객체만을 받기위해서는 <T extends “parent class”>로 범위를 한정지을 수도 있음.

public class GenericTest<T> implements Serializeable{
  private T testObject;
  public void setObject(T testObject){
    this.testObject = testObject;
  }
  public T getObject(){
    return this.testObject;
  }
}

public static void main(String[] args){
  GenericTest<String> test = new GenericTest<String>();
  genericMethod(test, "abc")
}

// 객체의 값을 추가하는 방법.
public <T> void genericMethod(GenericTest<T> c, T addedValue) {
  c.setObject(addedValue);
  T value = c.getObject();
  Systems.out.println(value); /// "abc"
}

5. Collection - List

Data Structure - 자료 구조 : 어떤 정보를 담는 것. 하나의 데이터가 아닌 여러 데이터를 담을 때. Ex) 배열, 리스트, 큐, 맵

  • List: 순서가 있는 목록
  • Set: 순서와 중복이 없는 목록
  • Queue: 먼저 들어온 것이 먼저가는 목록
  • Map: Key-Value의 쌍의 목록
public interface Collection<E> extends Iterabla<E>

Iterable의 상속 받았기 때문에 반복을 하는 iterator(), hasNext(), next(), remove() 메소드 구현이 필요.

ArrayList

한가지 종류의 객체를 저장할때.

만일 여러 종류의 객체가 필요하다면? DTO를 만들어서 하나의 객체로 담음.

아무런 값의 선언이 없이 생성자를 호출하면 기본 크기는 10으로 만들어짐.

  • add(): 값을 추가할때.
  • addAll(): 컬렉션의 값들을 한번에 추가할때
  • size(): 배열에 담겨져있는 객체들의 사이즈. 배열의 length는 선언된 크기를 의미.
  • toArray(): 리스트를 배열로 변환할때.
ArrayList vs Vector

ArrayList는 Thread Safe하지 않지만, Vector는 Thread Safe함.

Stack(FIFO : First Input Last Out)

목록에서 가장 처음들어간 값이 가장 마지막으로 나옴.

6. Set And Queue

Set?

순서에 상관 없이, 데이터가 존재하는지 확인하는 용도. 중복을 방지하면서, 원하는 값이 포함되어 있는지 확인.

  • HashSet: 데이터의 순서가 전혀 필요 없음.
  • TreeSet: 데이터의 값에 따라 red-black 정렬.
  • LinkedHashSet: 저장된 순서에 따라 값이 정렬.
로드 팩터

로드 팩터 = 데이터의 개수 / 저장공간.

로드팩터가 증가하게되면, 저장 공간의 크기가 증가하기 때문에 재정리 작업이 필요해짐.

HashSet의 값은 For문을 돌면서 꺼낼 수 있음.

for(String temp: carSet) {
	System.out.println(temp);
}

이외에도 contains()를 통해 값이 존재하는지, remove()를 통해 값을 삭제할 수 있음.

Queue(LIFO : List In First Out)

LinkedList에 A를 넣으면 A는 시작이자 끝.

다음으로 B를 넣으면 리스트의 시작은 A이고, 끝은 B임.

다음으로 C를 넣으면, 시작은 A 끝은 C 그리고 B의 다음은 C임. 하지만 A는 B의 다음이 어떤 값인지 모르고, C역시 B의 앞이 누구인지 모름.

따라서 큐는 마지막의 들어온 값을 먼저 빼내면서, 리스트를 소비하고 싶을때 사용.

  • push(): 리스트의 앞에 값을 추가.
  • add(), offer(), set(): 리스트의 뒤에 값을 추가.
  • peek(): 맨앞 데이터를 리턴.
  • get(): 값을 가져옴.
  • pop(): 리스트의 가장 뒤에 있는 값을 삭제하고 리턴.

7. Map

참조

자바의 신 VOL.2 - 이 상민 지음