기존 인코딩 방식이 여러 개인 이유는
“기술이 복잡해서”가 아니라, 컴퓨터 역사 + 국가/OS/시대별 타협의 결과다.
문자는 원래 1바이트로 표현하기 어려웠고,
각 나라와 OS는 자기 언어를 처리하기 위해 각자 다른 방식을 만들었다.
그런데 국제 표준(Unicode)이 늦게 정착되면서
이미 쓰이던 인코딩들이 그대로 남게 되었다.
그래서 오늘날까지도 다음과 같은 인코딩이
레거시 데이터로 존재한다.
현재 전 세계적으로 사실상 표준은 UTF-8이다.
UTF-8은 텍스트 기반 데이터에서만 의미가 있다.
이미지, mp3, zip 같은 바이너리 파일에는 적용 개념이 없다.
UTF-8을 이해하려면 먼저 Unicode를 이해해야 한다.
“전 세계 모든 문자를 하나의 표로 정리하자”
초기에는 65,536 문자면 충분할 것이라고 생각했다.
문자 = 번호(code point)
Unicode는 문자를 번호로 치환하는 개념이다
예시:
U+0041 U+AC00 U+1F600 Unicode 자체는 저장 방식이 아니다.
그저 “이 문자는 이 번호다”라는 약속이다.
U+0000 ~ U+10FFFF
0x10FFFF = 1,114,111Unicode는 하나의 평면이 아니라
17개의 Plane(평면) 으로 구성되어 있다.
| Plane | 이름 | 범위 | 예시 |
|---|---|---|---|
| 0 | BMP | U+0000 ~ U+FFFF | 가, 漢 |
| 1 | SMP | U+10000 ~ U+1FFFF | 😀 |
| 2 | SIP | U+20000 ~ U+2FFFF | 확장 한자 |
| 16 | Private Use | U+100000 ~ U+10FFFF | 사용자 정의 |
초기 Unicode의 의도는 다음과 같았다.
Plane 0 하나에 전 세계 모든 문자를 담는 것
하지만 한자 수가 너무 많아 실패했다.
그래서:
언어별 위치는 다음과 같다.
Plane 0은 각 언어에서
“기본적이고 일상적으로 쓰이는 문자 집합”이 배치된 곳이다
UTF-8은 Unicode를 실제로 저장·전송하기 위한 구현 방법 중 하나다.
Unicode가 번호 체계라면,
UTF-8은 그 번호를 바이트로 표현하는 방식이다.
UTF-8은 가변 길이 인코딩이다.
| 길이 | 패턴 | payload 비트 |
|---|---|---|
| 1바이트 | 0xxxxxxx | 7비트 |
| 2바이트 | 110xxxxx 10xxxxxx | 11비트 |
| 3바이트 | 1110xxxx 10xxxxxx 10xxxxxx | 16비트 |
| 4바이트 | 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx | 21비트 |
문자에 따라 1~4바이트만 사용한다.
UTF-8은 ‘언어의 개수’를 기준으로 하지 않는다.
유니코드 코드포인트 값이 들어갈 수 있는 최소 바이트 수를 사용한다.
U+7F7F를 UTF-8로 인코딩U+7F7F
0111 1111 0111 1111
10진수: 32639 → 3바이트 문자
1110xxxx 10xxxxxx 10xxxxxx
1110 0111 10 111101 10 111111
11100111 10111101 10111111
UTF-8: E7 BD BF
Unicode는 본질이고,
UTF-8은 구현이다.