MySQLの整数データ型 INT/TINYINT/SMALLINT/MEDIUMINT/BIGINT を考える

数値のデータ型を大きく分けると、整数型、小数点型、ビット型がありますが、今回は、整数型に焦点を絞ります。
CREATE TABLE文で、たとえばデータ型 INT のカラムを作成する場合に下記のように指定して使いますが、このときの M、UNSIGNED、ZEROFILLの意味を改めて考えてみたいと思います。

CREATE TABLE tablename(
columnname INT[(M)] [UNSIGNED] [ZEROFILL]
)

整数型

MySQLで使える整数型には、INT、SMALLINT、TINYINT、MEDIUMINT、BIGINT の5つがあります。
それぞれの違いは記憶域のサイズです。
適切にデータ型を選択することでシステムを効率的に使えるようになります。
記憶域のサイズによって、挿入できる最大値が決まります。
*SIGNEDとUNSIGNEDについては後述します。

データ型 記憶域のサイズ SIGNEDの場合 INSIGNEDの場合
TINYINT 1バイト -128 ~ 127 0 ~ 255
SMALLINT 2バイト -32768 ~ 32767 0 ~ 65535
MEDIUMINT 3バイト -8388608 ~ 8388607 0 ~ 16777215
INT 4バイト -2147483648~ 2147483647 0 ~ 4294967295
BIGINT 8バイト -2の63乗~2の63乗-1 0 ~ 2の64乗-1

M(最大表示幅)

冒頭のCREATE TABLE文の例にあった「INT[(M)]」の M は最大表示幅を示します。
「INT(3)」とすると3桁格納でき、3桁表示されます。
「1」を挿入するとスペースが2つと数字の「1」が、つまり「(スペース)(スペース)1」が挿入されるわけです。
この(スペース)をゼロに自動置換するのが次に説明するZEROFILL属性です。

*整数データ型の表示幅属性は、MySQL 8.0.17では非推奨になり、将来のバージョンではサポートされなくなる予定です。

ZEROFILL(ゼロ埋め処理)

挿入された値が M桁 に満たない場合、左から「0」を自動挿入します。
たとえば、INT(3) の場合で「1」を挿入した場合、「001」となります。

ZEROFILLを指定した場合、自動的にUNSIGNEDも追加されます。
よって、マイナスの値を挿入できなくなります。

*ZEROFILL属性は、MySQL 8.0.17では非推奨になり、将来のバージョンではサポートされなくなる予定です。

SIGNEDとUNSIGNED

整数のデータ型にはSIGNEDとUNSIGNEDを指定できます。
SIGNEDは署名済、UNSIGNEDは未署名とも言われ、「+」や「-」の符号を付ける(SIGNED)か付けない(UNSIGNED)かを表しています。

1バイト(8ビット)しか使わないTINYINTを例に、挿入できる値について説明します。
SIGNEDの場合、1ビットは符号で使われますから、TINYINTは残りの7ビットに数値が入ります。
つまり、挿入できる値の範囲は2進数表記で、符号がマイナス「1」、プラス「0」とした場合、10000000~01111111。10進数表記だと-128~127となります。

UNSIGNEDの場合は符号がないので、8ビット全部使えます。
なので、同じく挿入できる値の範囲は2進数表記で 00000000~11111111(10進数で0~255)となります。