본문 바로가기
Java/Effective Java 3E

[이펙티브자바 3판] ITEM36. 비트 필드 대신 EnumSet을 사용하라

by 잭피 2020. 11. 8.

이번장의 핵심은...

열거할 수 있는 타입을 한데 모아 집합 형태로 사용한다고 해도 비트 필드를 사용할 이유는 없다

EnumSet 클래스가 비트 필드 수준의 명료함과 성능을 제공하고

아이템 34에서 설명한 열거 타입의 장점까지 선사하기 때문이다

EnumSet의 유일한 단점이라면 불변 EnumSet을 만들 수 없다는 것다

그래도 향후 릴리스에서는 수정되리라 본다

그때까지는 Collections.unmodifiableSet으로 EnumSet을 감싸 사용할 수 있다


비트필드

// 비트 필드 열거 상수 - 구닥다리 기법
public class Text {
  public static final int STYLE_BOLD   = 1 << 0; // 이진수 1 =1
  public static final int STYLE_ITALIC = 1 << 1; // 이진수 10 = 2
  public static final int STYLE_UNDERLINE = 1 << 2; // 이진수 100 = 4
  public static final int STYLE_STRIKETHROUGH = 1 << 3; // 이진수 1000 = 8

  // 매개변수 styles는 0개 이상의 STYLE_ 상수를 비트별 OR한 값이다
  public void applyStyle(int styles) {...}
}

text.applyStyle(STYLE_BOLD | STYLE_ITALIC);

비트별 OR을 사용해 여러 상수를 하나의 집합으로 모을 수 있고,

이런 집합을 비트 필드라고 한다

 

비트 필드를 사용해 합집합, 교집합 같은 집합 연산을 효율적으로 수행

하지만, 비트 필드는 정수 열거 상수(ITEM 34)의 단점을 그대로 지니고, 추가로 아래 문제도 있음

 

비트 필드 값이 그대로 출력되면 단순한 정수 열거 상수를 출력할 때보다 해석하기 훨씬 어려움

최대 몇 비트가 필요한지를 API 작성 시, 미리 예측하여 적절한 타입을 선택해야 함

API를 수정하지 않고는 비트 수를 더 늘릴 수 없다

EnumSet 클래스

열거 타입 상수의 값으로 구성된 집합을 효과적으로 표현해준다

// 비트 필드를 대체하는 현대적 기법
public class Text {
	public enum Style {
		BOLD, ITALIC, UNDERLINE, STRIKETHROUGH
	}

	// 어떤 Set을 넘겨도 되나, EnumSet이 가장 좋다
	public void applyStyles(Set<Style> styles){
	System.out.printf("Applying styles %s to text%n",
                Objects.requireNonNull(styles));
	}
}
// 사용 예
public static void main(String[] args) {
    Text text = new Text();
    text.applyStyles(EnumSet.of(Style.BOLD, Style.ITALIC));
}

- applyStyles 메서드의 파라미터로 EnumSet<Style>이 아닌 Set<Style>을 받은 이유?

-> 모든 클라이언트가 EnumSet을 건네리라 짐작되는 상황이라도 이왕이면 인터페이스로 받는 게 일반적으로 좋은 습관이다

 

 

 

이 글은 “이펙티브 자바 3판” 책 내용을 정리한 글입니다.

만약 저작권 관련 문제가 있다면 “shk3029@kakao.com”로 메일을 보내주시면, 바로 삭제하도록 하겠습니다.

 

댓글