비트마스크를 배열로 관리하는 bitsToArrays.js

2019. 1. 9. 19:36Programming/JavaScript

반응형

Javascript에서 비트마스크를 쓸 일이 있을까?

=====

임베디드 장비에서 서버를 돌렸기 때문에, 꽤 많은 기능들은 비트마스크로 관리됐다. 이벤트가 on/off됐다던가, 장비에 연결된 장치들과 연결이 끊어졌다던가, 이런 상태들을 한번에 관리하기엔 비트마스크만한 게 없었다. 뭣보다 워낙 옛날에 C로 코드를 작성하던 아저씨들이 만든 코드라, 비트마스크를 쓸 일이 상당히 많았다.

여러개의 Boolean값을 사용하고 있다면, 비트마스크를 통해서 메모리 효율을 늘릴 수 있을 것이다.


비트마스크가 효율적이긴 한데...

=====

event_status라는 비트마스크에 n번째 비트가 설정되었는지 확인하려면, 다음과 같이 작성하면 된다.


```

if ((event_status & (1<<n)) !== 0) {

  /*비트마스크가 설정됐다.*/

} else {

  /*비트마스크가 설정되지 않았다.*/

}

```


간단하다. 하지만 64비트짜리 비트마스크를 설정하고, 확인하려면 어떻게 해야할까?

```

event_status |= (1<<63);

console.log(event_status & (1<<63)); //-2147483648을 반환한다.

```


잘 동작하는 것 같다. 하지만 다음과같이 확인해보자.

```

console.log(event_status & (1<<31)); //여전히 -2147483648를 반환한다.

```


뭔가 이상하지 않는가? 그렇다. 오버플로가 발생한다. 애시당초 Javascript의 number의 범위는 -(2^53-1) ~ (2^53-1)이다. [참고: Javascript에서 표현 할 수 있는 숫자의 범위는 얼마나 되나?](http://lambdaexp.tistory.com/59) [참고2: Javascript Number 범위](http://ouoiouoi.blogspot.com/2017/05/javascript-number.html)


간단히 말하면 64비트의 비트마스크가 필요할 경우, 이를 제대로 관리할 수 없다. 따라서 number값을 두 개 선언한 후 관리해야한다. 영 성가신대다가 코드가 길면 길수록 두 개의 변수값을 좇아다니다보면 스파게티 코드가 만들어지는 건 순식간이다. 게다가 새로 들어오신 분이 비트마스크 연산을 잘 이해를 못해서 작성한 코드다. ~~~웃기게도 만들어놓고 실제로 사용은 하지 않았는지, get을 이용해서 비트마스크를 확인하면 해당 비트값이 초기화되는 문제가 있었다. 오늘 README.md 파일을 정리하다 발견해서 수정해놨다.~~~


[bitsToArrays.js](https://github.com/zerodice0/bitsToArray.js)

=====

README.md에 최대한 자세히 써놨다. 간단히 요약하면 내부에 number형 배열을 생성해서 비트마스크를 관리하는 객체다. 예를 들어서 set(0)을 호출하면 배열의 첫번째 number의 값이 1(0x00000001)이되며, set(1)을 호출하면 배열의 첫번째 number의 값이 3(0x00000011)이 된다. set(32)를 호출하면? 배열의 두 번째 값에 1(0x00000001)이 할당되며, get(32)를 통해서 마치 33번째 비트마스크가 설정된 것처럼 동작할 수 있다.


여담이지만 set(64)를 호출하면 배열에 값을 하나 추가한 뒤 비트마스크를 설정한다. 세 번째 값이 1(0x00000001)로 설정된다. get()는 비트마스크가 설정되어있을 경우에는 0이 아닌 값을, 설정되지 않았을 경우에는 0을 반환한다. 만약 Boolean값으로 받고싶다면, getBoolean()를 사용하면 된다. getBoolean을 사용하면 비트마스크가 설정되어있을 때 true를, 설정되지않았을 때 false를 반환한다.

반응형