갑자기 bit를 얼마나 할당하는가에 따라서 얼만큼의 시간을 표현할 수 있을까라는 생각이 들었습니다. 흔히 unix timestamp 라고 해서 1970년 1월 1일 0시 부터 현재까지를 Second 단위로 표현한 것입니다. unix timestamp 는 4 bytes 로 표현되고, 이를 2038년 1월 19일 03:14:07 에 overflow 가 난다고 합니다. 그럼 이를 어떻게 계산할 수 있을까요? 사실 원리는 간단합니다. 일단 다음과 같이 시간을 정리해 봅시다. (윤달은 일단 빼고 계산합니다.)
1 minute | 60 seconds |
1 hour | 60 * 60 = 3600 seconds |
1 day | 60 * 60 * 24 = 86400 seconds |
1 weak | 60 * 60 * 24 * 7= 604800 seconds |
1 year | 60 * 60 * 24 * 365 = 31536000 seconds |
이제 이런 시간 테이블이 있으니 생각해보면 4 bytes는 32 bits 이므로 2^32 승입니다. 이것을 간단히 구하면 다음과 같습니다.
>>> pow(2, 32) / 60 / 60 / 24
49710.26962962963
>>> pow(2, 32) / 60 / 60 / 24 / 365
136.19251953323186
4 bytes 로는 Day 로는 49710일, Year 로는 136년을 커버할 수 있습니다. 이러면 1970 + 136 해서 2106년이 나옵니다. 뭔가 이상하지 않나요? 위에서 제가 2038년에 1월 19일 이라고 했는데, 왜 2106년이 나올까요? 사실 이건 간단합니다. unix timestamp 는 time_t(부호가 있는 4 bytes)를 이용하기 때문입니다. 그래서 실제로 32 bits가 아니라 31 bits만 사용하게 됩니다. 31bit 로 계산하면 다음과 같이 68년 1970 + 68년 해서 2038년에 만료가 되는 것입니다.
>>> pow(2, 31) / 60 / 60 / 24
24855.134814814814
>>> pow(2, 31) / 60 / 60 / 24 / 365
68.09625976661593
그렇다면 이제 이걸 위해서 시간 값을 사용하면 bit를 얼마나 할당해야 할까요? unix timestamp 는 seconds 단위지만, 현재는 milliseconds 단위는 최소 커버해야 합니다. 여기서 공식은 다음과 같습니다.
>>> pow(2, N) / 1000 / 60 / 60 / 24 / 365
계산해보면 다음과 같습니다.
Bits | Year |
37 bits | 4.35 |
38 bits | 8.71 |
39 bits | 17.43 |
40 bits | 34.86 |
41 bits | 69.73 |
42 bits | 139.46 |
43 bits | 278.92 |
보통 자신만의 unique key를 만들기 위해서 시간 값을 집어넣는데, 현재 시간을 epoch을 잡는다면 위와 같이 사용이 가능합니다. 서비스가 얼마나 갈지는 모르지만, 최소 39 bit 는 되어야 key 사용이 가능할듯 하네요. 안전하게 할려면 40 bit 이상은 가야할듯 합니다. twitter 의 snowflake 는 42 bit를 사용하고 있습니다.