비트필드 혹은 플레그 라고도 하는데 어떤 변수의 각 비트마다 서로다른 상태를 저장하는것이다.
그리고 각 상태는 2의 제곱수들(1,2,4,8,16,32...)로 이루어진다. 그리고 그 상태를 and,or,not 을 이용해서 여러가지 상태를 한번에 저장하고 확인하는것이다.
이런 비트 필드는 속도도 빠르고 메모리 공간도 적게 차지 하지만 비트연산을 하나 잘못하게되면 대참사를 일으킬 수 있다.

그런이유로 EnumSet 라는것을 사용하면 좋다고 하는것이다. 일반적으로 Enum은 상수표현도 하겠지만 상태를 표시하기 위해서 사용하는 경우도 많다.  그렇다면 현재상태를 비트필드처럼 동시에 표시하려면? 여러가지 자료구조가 있겠지만 Set 이라는 집합 자료구조를 사용하면 좋다. 실수로 두번 넣는다고 두개가 들어가지 않고 두번 뺀다고 다른 데이터에 영향을 주지도 않으며 동시에 여러개를 저장해줄수도 있다.

그렇다면 기능상 비트필드와 집합이 다르지 않다고 한다면 처리속도나 사용되는 메모리 용량은 어떨까?
Set의 구현에 따라 다르겠지만 hashset의 경우에는 배열을 이용하고 hash코드를 이용하기 때문에 hashcode 계산하는 시간도 걸릴것이고 상태를 저장하기 위한 배열도 필요하다. 그렇다면 비트필드에 비해 너무 비효율적인것이 아닌가? 라고 생각할수 있지만 여기서 EnumSet 이라는것이 등장한다.
EnumSet은 저장되는 Enum의 원소 갯수가 64개를 넘지 않는다면 long 형식의 비트필드를 내부적으로 사용한다. 즉 껍데기는 Set이지만 내용물은 비트필드인것이다. 따라서 Set을 사용하듯이 특별히 and,or, not 등의 연산에 대해서 고민하지 않고 add,remove등의 메소드 만으로 비트필드에 가까운 성능과 콜렉션을 이용한 안정성을 동시에 보장하는것이다.

EnumSet의 생성은 여러 enum을 동시에 쓰기 때문에 쉽게 생성이 가능한 static 팩토리 메소드를 다양하게 제공하는데 그중 EnumSet.of 메소드를 예를 들고 있다.
of의 인자로 사용하려는 enum의 원소를 모두 적어주면 그것을 표현하는 EnumSet을 생성해준다.

마지막으로 EnumSet의 단점이라면 불변타입(final 비트필드 같은것)을 생성할수 없다는것이다. Collections.unmodifiableSet 이라는 것을 사용하면 가능하지만 불편하긴하다. 아마 차후 배포판에서 분명이 개선될 것이다. 라고 하는데 1.6 기준으로 써진 책인데 차후버전인 java 1.7에서는 이런 개선은 아직 보이지 않는다.

Posted by 동적할당
: