一. 建表规范
1.使用InnoDB引擎
无特殊情况必须使用InnoDB引擎(5.5版本后默认引擎)
InnoDB支持事务、行级锁、MVCC,并发性能更好,CPU及内存缓存页优化使得资源利用率更好。
2.规范表、字段的命名
表名、字段名,小写下划线风格,尽量做到见名知意。
3.规范索引命名
主键索引名为pk_表名_字段名,唯一索引名为uk_表名_字段名,普通索引为idx_表名_字段名。
4.字段NOT NULL的好处
NULL的列使索引、索引统计、值得比较都更加复杂;
NULL类型MySQL内部需要特殊处理,增加处理记录的复杂性,NULL的列需要额外的空间来标识;
对NULL的处理是能采用IS NULL或IS NOT NULL:WHERE name != '张三'; 的查询结果不会包含name为NULL的记录。
5.char与varchar
如果存储的字符串长度固定,则应该使用char定长字符串类型,存取效率较高;
如果字符串长度不固定,则应该使用varchar变长字符串类型,它会根据字符串实际长度分配空间,节约资源。如果字符串长度超过5000,应该定义字段类型为text等大文本,并独立一张表,用主键关联,避免影响其他字段的索引效率。
二. 索引规范
1.善于使用唯一索引
业务上具有唯一特性的字段,即使是多个字段组成,也必须建成唯一索引,唯一索引可以显著提高查询效率(普通索引又称左前缀索引,如果字段过长(767bytes)只会索引字段的前一部分,而唯一索引则索引整个字段)。
2.最左前缀原则
索引文件具有B+Tree的最左前缀匹配特性,如果最左边的值未确定,那么无法使用此索引。建立联合索引时,区分度最高的字段放在最左边。
3.控制索引数量
单表索引建议控制在5个以内,联合索引不超过5个字段。
4.慎重建立索引
禁止在更新频繁、区分度不高的列上建立索引;
更新会变更B+Tree,大大降低性能;
"性别"这种区分度不大的属性,建立索引是无意义的,性能与全表扫描相似。
5.关联查询时要注意关联字段的类型
进行关联查询时,保证被关联字段要有索引,且数据类型一致,防止因字段类型不同造成隐式转换,导致索引失效。
三. SQL语句
1.慎用SELECT *
建议不要使用SELECT *,只获取必要的字段,读取不必要的列会增加CPU、IO、NET的消耗。
同时,SELECT *容易在增加或者删除字段后出现bug。
2.禁止使用隐式转换
WHERE id = 1201800992222222;
id如果是字符串类型会产生隐式转换,导致全表扫描。
3.禁止在WHERE条件属性上使用函数
WHERE CAST(create_time AS SIGNED) < 20190708180606;
通过CAST函数,将日期转换成整数类型,导致全表扫描。
4.统计函数的陷阱
当某一列全为NULL时,COUNT(col)返回0,使用SUM(col)返回NULL,统计函数不会将NULL值加入计算。
5.IN与EXISTS
已知A、B两张表:
A:100000 B:100
SELECT * FROM A WHERE A.id IN (SELECT id FROM B);
大表 IN 小表,效率较高:小表可以被加载到内存,大表可以命中索引(IN中的内容尽量不要超过200)。
A:100 B:100000
SELECT * FROM A WHERE EXISTS (SELECT * FROM B WHERE B.id = A.id);
小表EXISTS大表,效率较高:小表执行全表扫描,大表可以命中索引。
6.表关联需注意
表关联应该尽量遵循小表驱动大表的原则;
A LEFT JOIN B时应注意:ON条件是关联前的筛选,WHERE条件是关联后的筛选;
SELECT * FROM A LEFT JOIN B ON A.id = B.id AND B.name = 'z' WHERE a.age > 20; --如果A匹配10条记录,B只有1条记录匹配,最终返回10条记录;
SELECT * FROM A LEFT JOIN B on A.id = B.id WHERE a.age > 20 AND B.name = 'z'; --如果A匹配10条记录,B只有1条记录匹配,最终返回1条记录;
7.善于使用EXPLAIN
分析SQL的执行效率,先复现场景,以EXPLAIN的结果为准,至少要达到 range 级别。
(1)consts 单表中最多只有一个匹配行(主键或者唯一索引)。
(2)ref 指的是使用普通的索引(normal index)。
(3)range 对索引进行范围检索。
(4)index 全索引扫描(索引物理文件全扫描,速度非常慢,这个 index 级 别比较 range 还低,与全表扫描是小巫见大巫)。
(5)all 全表扫描
来源:CSDN
作者:sunny david jin
链接:https://blog.csdn.net/qq_35936776/article/details/103840080