Mysql schema与数据类型优化


内容学习自《高性能MySQL》

数据类型选择

  • 更小的通常更好

尽量使用可以正确存储数据的最小类型。占用的更小的磁盘、内存和CPU缓存

  • 简单就好

简单的数据操作通常需要更少的CPU周期,整形比字符串操作的代价更低,因为字符集合校对规则使字符比整数更复杂

  • 尽量不使用NULL

通常最好指定列为NOT NULL,除非真要存储NULL值。如果查询中包含NULL的列,更难优化,因为NULL的列使得索引、索引统计和值的比较更复杂。
当可为NULL的列被索引时,每个索引记录需要一个额外的字节,如果计划在列上建立索引,应建立避免为NULL,InnoDB使用单独的位(bit)来存储NULL
对稀疏数据(很多值为NULL)有很好的空间效率

  • 保存时间

TIMESTAMP只需要4个字节,而DATETIME需要8个字节,TIMESTAMP表示的时间范围小(1970-2038),但是可以区分时区
不推荐保存Unix整数,因为这样带不来任何收益

  • 整数

对于储存计算来说INT(1)和INT(20)是相同的

  • 实数

对于DECIMAL可以考虑BIGINT代替,只需乘相应的倍数

  • VARCHAR CHAR

VARCHAR需要1-2个字节额外记录字符串长度,小于255使用1个字节,变长UPDATE时间会久一点,
合适使用:字符串列的最大长度比平均长度大很多;列的更新很少,碎片不是问题;使用UTF-8这样的字符集;

例如存储MD5值,不容易产生碎片

使用VARCHAR(5)和VARCHAR(200)存储hello字符的空间开销是一样的,那么使用更短的列有什么优势吗?
事实证明,更长的列会消耗更多的内存,因为MySQL通常会分配固定大小的内存块来保存内部的值,尤其是使用临时表进行排序或者操作。
最好是分配真正需要的空间

  • BLOB TEXT

这两个都会被当做独立的对象处理,存储引擎在存储时会做额外的处理,长度太长时,会使用指针来指向实际值。
BLOB没有排序规则,排序时也不同,只去前面的多少个字节,索引也一样

  • ENUM

枚举在内部保存的是整数,所以没有必要使用数字作为ENUM常量,枚举字段的排序时按照内部的整数来排的,要么使用FIELD()函数指定

  • 保存IP

IP其实是一个32位的数字,所以使用int储存更好,而不是VARCHAR或者CHAR


文章作者: 江湖义气
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 江湖义气 !
  目录