MySQL을 사용하다 보면 INT(1)과 TINYINT(1)처럼 자료형 뒤에 괄호로 숫자를 지정하는 경우를 자주 접하게 됩니다. 많은 개발자가 이 숫자가 저장 가능한 값의 크기를 제한한다고 오해하지만, 실제로는 전혀 다른 의미를 가집니다.
괄호 안 숫자의 의미: 표시 너비(Display Width)
먼저 알아야 할 핵심은, 괄호 안의 숫자 1은 단지 화면에 표시되는 너비(display width)를 나타낼 뿐이라는 점입니다. 즉, INT(1)과 TINYINT(1) 모두 이 숫자가 실제 저장 공간이나 값의 범위에는 아무런 영향을 주지 않습니다.
두 자료형의 진짜 차이는 저장 용량과 값의 범위에 있습니다.
- TINYINT: 1바이트를 차지하며, 범위는 -128부터 +127까지입니다.
- INT: 4바이트를 차지하며, 범위는 -2147483648부터 +2147483647까지입니다.
따라서 참/거짓 같은 작은 값을 저장할 때는 TINYINT가 메모리를 절약할 수 있는 반면, 큰 숫자를 다뤄야 한다면 INT를 사용해야 합니다.
ZEROFILL로 확인하는 표시 너비의 역할
그렇다면 표시 너비는 언제 의미가 있을까요? 바로 ZEROFILL 옵션과 함께 사용할 때입니다. 먼저 예제 테이블을 만들어 보겠습니다.
mysql> create table intAndTinyint −> ( −> FirstNumber int(1) zerofill, −> SecondNumber tinyint(1) zerofill −> ); Query OK, 0 rows affected (0.52 sec)
이제 테이블에 데이터를 삽입해 보겠습니다.
mysql> insert into intAndTinyint values(1,1); Query OK, 1 row affected (0.32 sec) mysql> insert into intAndTinyint values(12,12); Query OK, 1 row affected (0.26 sec) mysql> insert into intAndTinyint values(123,123); Query OK, 1 row affected (0.14 sec)
SELECT 문으로 전체 레코드를 조회해 보겠습니다.
mysql> select *from intAndTinyint;
실행 결과는 다음과 같습니다.
+-------------+--------------+ | FirstNumber | SecondNumber | +-------------+--------------+ | 1 | 1 | | 12 | 12 | | 123 | 123 | +-------------+--------------+ 3 rows in set (0.00 sec)
여기서 중요한 점은, 지정된 너비보다 실제 값의 자릿수가 더 크면 값이 잘리거나 제한되지 않고 그대로 저장·출력된다는 사실입니다. 위 예제에서 int(1) 컬럼에 3자리 숫자인 123이 그대로 들어간 것을 확인할 수 있습니다.
너비를 늘려 ZEROFILL 동작 살펴보기
이번에는 괄호 안의 숫자를 1보다 크게 설정했을 때 ZEROFILL이 어떻게 동작하는지 INT 자료형만으로 예시를 통해 알아보겠습니다. 먼저 테이블을 생성합니다.
mysql> create table intVsIntAnyThingDemo −> ( −> Number1 int(11) unsigned zerofill, −> Number int(13) unsigned zerofill −> ); Query OK, 0 rows affected (1.17 sec)
INSERT 명령으로 레코드를 삽입합니다. 여기서는 두 컬럼에 서로 다른 너비(11과 13)를 지정했습니다.
mysql> insert into intVsIntAnyThingDemo values(12345,6789); Query OK, 1 row affected (0.44 sec) mysql> insert into intVsIntAnyThingDemo values(3,2); Query OK, 1 row affected (0.20 sec) mysql> insert into intVsIntAnyThingDemo values(12,89); Query OK, 1 row affected (0.15 sec) mysql> insert into intVsIntAnyThingDemo values(123,6789); Query OK, 1 row affected (0.17 sec) mysql> insert into intVsIntAnyThingDemo values(1234,6789); Query OK, 1 row affected (0.14 sec)
SELECT 문으로 전체 레코드를 조회해 보겠습니다.
mysql> select *from intVsIntAnyThingDemo;
아래 출력 결과에서 서로 다른 너비와 ZEROFILL이 적용된 모습을 확인할 수 있습니다.
+-------------+---------------+ | Number1 | Number | +-------------+---------------+ | 00000012345 | 0000000006789 | | 00000000003 | 0000000000002 | | 00000000012 | 0000000000089 | | 00000000123 | 0000000006789 | | 00000001234 | 0000000006789 | +-------------+---------------+ 5 rows in set (0.00 sec)
Number1 컬럼은 너비가 11이므로 11자리에 맞춰 앞부분이 0으로 채워졌고, Number 컬럼은 너비가 13이므로 13자리에 맞춰 0이 채워진 것을 볼 수 있습니다.
정리
INT(1),TINYINT(1)등 괄호 안 숫자는 표시 너비일 뿐, 저장 용량이나 값의 범위에는 영향을 주지 않습니다.- TINYINT는 1바이트(-128 ~ +127), INT는 4바이트(-2147483648 ~ +2147483647)를 사용합니다.
- ZEROFILL 옵션을 사용하면 지정한 너비만큼 앞자리가 0으로 채워져 출력됩니다.
- 값이 지정된 너비보다 길어도 잘리지 않고 그대로 저장됩니다.
- 참고로 MySQL 8.0부터는 정수 자료형의 표시 너비가 더 이상 권장되지 않으므로, 새 프로젝트에서는 가급적 사용하지 않는 것이 좋습니다.