Effective Java 61. 박싱된 기본 타입보다는 기본 타입을 사용하라

Jung Ho Seo·2020년 8월 22일
0

EffectiveJava

목록 보기
17/35
post-thumbnail
post-custom-banner

Primitive Type

자바의 데이터 타입은 크게 두 가지로 나눌 수 있다. 바로 int, double, boolean 같은 기본 타입과 String, List 같은 참조 타입이다. 그리고 각각의 기본 타입에는 대응하는 참조 타입이 하나씩 있으며, 이를 박싱된 기본 타입이라고 한다. 예건태 int, double, boolean에 대응하는 박싱된 기본 타입은 Integer, Double, Boolean이다.

오토박싱과 오토언박싱 덕분에 두 타입을 크게 구분하지 않고 사용할 수는 있지만, 그렇다고 차이가 사라지는 것은 아니다. 둘 사이에는 분명한 차이가 있으니 어떤 타입을 사용하는지는 상당히 중요하다. 주의해서 선택해야 한다는 말이다.

기본 타입과 박싱된 타입의 차이점

둘 사이의 차이점은 크게 세가지이다.

  1. 기본 타입은 값만 가지고 있으나, 박싱된 타입은 값에 더해 식별성(identity)이란 속성을 가진다. 달리 말하면 박싱된 기본 타입의 두 인스턴스는 값이 같아도 서로 다르게 식별될 수 있다.
  2. 기본 타입의 값은 언제나 유효하나, 박싱된 기본 타입은 유효하지 않은 값, 즉 null을 가질 수 있다.
  3. 기본 타입이 박싱된 기본 타입보다 시간과 메모리 사용면에서 더 효율적이다.

Integer 값을 오름차순으로 정렬하는 비교자

Comprator<Integer> naturalOrder = (i, j) -> (i <j) ? -1 : (i == j ? 0 : 1);

이 비교자는 거의 대부분의 상황에서 잘 작동하지만 오류가 있다

natuarlOrder.compare(new Integer(42), new Integer(42));

값을 출력해보자, 두 Integer 인스턴스의 값이 42로 같으므로 0을 출력해야 하지만, 실제로는 1을 출력한다. 즉 첫번째 값이 크다고 주장한다.

원인은 뭘까? 두번째 검사 (==)를 Integer클래스로 진행할경우 두 객체간의 참조 식별성 검사를 진행하게 되고 이 값은 false가 된다.

실무에서 이러한 형태의 메서드를 활용하고 싶다면 기본 타입을 받는 정수로 바꾸어주는 처리를 해주어야한다.

int i = iBoxed, j = jBoxed; // 오토 박싱

기이하게 동작하는 프로그램

public class Unbelievable {
	static Integer i;
	
	public static void main(String[] args) {
		if(i == 42)
			System.out.println(“믿을 수 없군”);
	}
}

이 프로그램은 “믿을 수 없군”을 출력하지 않을 뿐더러 그만큼 기이한 결과를 보여준다. NullPointerException을 던지는 것이다. 원인은 i가 int가 아닌 Integer이며 다른 참조 필드처럼 Integer의 초기값 역시 0이란 말이다.

즉, i == 42는 Integer와 int를 비교하는 것이다. 거의 예외 없이 기본 타입과 박싱된 기본 타입을 혼용한 연산에서는 박싱된 기본 타입의 박싱이 자동으로 풀린다 그리고 null 참조를 언박싱하면 NullPointerExcpetion이 발생한다. 해결법은 간단한다. i를 int로 선언해주면 끝이다.

끔찍이 느린코드

public static void main(String[] args) {
	Long sum = 0L;
	for (long i = 0; i <= Integer.MAX_VALUE; i ++) {
		sum += i;
	}
}

이 코드는 끔찍이 느리다. 어디서 느려질까? sum을 += 하는 과정에서 박싱과 언박싱이 반복해서 일어나 체감이 될 정도로 성능이 느려진다.

박싱된 타입을 써야할 때

적절히 사용되는 경우가 많지는 않지만, 컬렉션의 원소, 키값으로 사용할 수 있다.

정리

기본 타입과 박싱된 기본 타입 중 하나를 선택해야 한다면 가능하면 기본 타입을 사용하라. 기본 타입은 간단하고 빠르다. 박싱된 기본 타입을 써야 한다면 주의를 기울이자.

profile
책, 글, 개발
post-custom-banner

0개의 댓글