萬盛學電腦網

您现在的位置: 萬盛學電腦網 >> 程式設計 >  >> 資料庫 >> MySQL 教學

MySQL INT(1) vs INT(11) 真相:顯示寬度 ≠ 存儲長度,ZEROFILL 才是關鍵

無數開發者誤以為 INT(1) 只能存 1 位數、INT(11) 存 11 位。實則 INT(M) 中的 M 僅為顯示寬度,與存儲範圍、佔用空間無任何關係。本文徹底釐清誤區,揭示 ZEROFILL 才是顯示寬度生效的前提。

核心結論先行

顯示寬度機制詳解

INT(M) 中的 M (1-255) 僅指示客戶端顯示時左側填充:

  • 無 ZEROFILL:左側填充空格(大多數客戶端忽略不顯示)
  • 有 ZEROFILL:左側填充0,且隱含 UNSIGNED

實測驗證


CREATE TABLE ccc (
    a INT(4), 
    b INT(20), 
    c INT(20) ZEROFILL
);

INSERT INTO ccc VALUES (4342343, 342, 342342);

SELECT * FROM ccc;
+---------+------+----------------------+
| a       | b    | c                    |
+---------+------+----------------------+
| 4342343 |  342 | 00000000000000342342 |
+---------+------+----------------------+
  • a INT(4):值 4342343 (7位) > 4,正常顯示,無截斷
  • b INT(20):值 342 (3位) < 20,客戶端可選填充空格,通常不顯示
  • c INT(20) ZEROFILL:強制左填 0 至 20 位,隱含 UNSIGNED

ZEROFILL 可視化效果

屬性INT(1)INT(11)說明
存儲字節4 字節4 字節完全相同
有符號範圍-2147483648 ~ 2147483647-2147483648 ~ 2147483647完全相同
無符號範圍0 ~ 42949672950 ~ 4294967295完全相同
顯示寬度111僅影響 ZEROFILL 填充
插入 9999999999 (10位)✅ 成功✅ 成功不受 M 限制
定義存入 1存入 99存入 9999存入 10000
INT(4) UNSIGNED ZEROFILL00010099999910000 (超寬不截斷)
INT(2) UNSIGNED ZEROFILL0199999910000
INT(4) (無 ZEROFILL)   1  99999910000
INT(2) (無 ZEROFILL) 199999910000

MySQL 整數類型完整對照

類型字節有符號範圍無符號範圍
TINYINT1-128 ~ 1270 ~ 255
SMALLINT2-32768 ~ 327670 ~ 65535
MEDIUMINT3-8388608 ~ 83886070 ~ 16777215
INT / INTEGER4-2147483648 ~ 21474836470 ~ 4294967295
BIGINT8-9223372036854775808 ~ 92233720368547758070 ~ 18446744073709551615

浮點/定點類型的顯示寬度


FLOAT(M,D) / DOUBLE(M,D) / DECIMAL(M,D)
M = 總位數(精度), D = 小數位數(標度)
-- 例:FLOAT(7,4) 可存 -999.9999 ~ 999.9999
-- 插入 999.00009 → 四捨五入為 999.0001

不同於整數,浮點類型的 (M,D) 確實限制存儲範圍和精度。

避坑指南

  1. 不要用 INT(M) 限制業務範圍:用 CHECK (age BETWEEN 0 AND 150) 或應用層驗證
  2. 遷移時警惕 ZEROFILL:導出導入可能丟失 ZEROFILL 屬性,導致前端顯示異常
  3. 臨時表複製陷阱:CREATE TEMPORARY TABLE ... SELECT * FROM t 可能不複製顯示寬度屬性
  4. ORM 映射誤區:Hibernate/MyBatis 生成 DDL 時常產生 INT(11),純屬歷史慣例,無實際意義

最佳實踐建議

  • 新建表省略顯示寬度:INT 而非 INT(11)
  • 需要前導零填充(如訂單號、員工號)才用 INT(6) ZEROFILL
  • 業務主鍵優先 BIGINT,預留 64 位空間
  • 狀態碼、枚舉值用 TINYINT UNSIGNED,省空間

INT(11) 是 MySQL 歷史遺留的「顯示寬度建議值」,與存儲零關係。拋棄誤解,關注真正影響存儲與性能的:類型選擇、UNSIGNED、ZEROFILL、索引設計。

copyright © 萬盛學電腦網 all rights reserved