为大家献上满满干货,社会你萧哥,人狠话不多
单表优化
单表数据一般以整型值为主的表在千万级以下,字符串为主的表在五百万以下是没有太大问题的。
1.字段
尽量使用 TINYINT、 SMALLINT、 MEDIUM_INT 作为整数类型而非 INT,如果非负则加上 UNSIGNED,这样存储不需要符号位,存得多,其次计算时用的非负数计算指令也更快
2.使用枚举或整数代替字符串类型,对于有些表,会有"男""女",这样简单的性别划分,其实不需要用字符串
3.单表不要有太多字段,建议在 20 以内, 因为 存储引擎要将数据取出后转换结构给服务层,越多的字段意味着每一行转换更费时间。如果是myisam,其结构正对服务层,姑且尚可。innodb可惨了,转换每一行之后再给服务层,得累死!
3.避免使用 NULL 字段,很难查询优化,且占用额外索引空间。索引中要额外分一位来标记是否为NULL。其次在统计查询时,NULL字段会使查询,聚集函数执行更复杂,步骤更多。
索引
1.索引并不是越多越好,要根据查询有针对性地创建,考在 WHERE 和 ORDER BY命令上涉及的列建立索引。
2.值分布很稀少的字段不适合建索引,例如"性别"这种只有两个值的字段,尽量对区分度大的字段建索引
3.长字符字段只建前缀索引,对于TEXT和超长varchar 建议使用index(left(‘字段’,10)),对前10个字符建立索引
4.字符字段最好不要做主键,主键必会变成索引,字符串做索引比整数低效
5.使用多列索引时注意顺序和查询条件保持一致,例如条件where A=a and B=b,建立索引(A,B),查询时才有用,(B,A)索引对此条件从句无效,触发全表扫描
查询SQL
1.可通过开启慢查询日志来找出较慢的 SQL,设置long_query_time变量找到慢查询
2.不写表达式:SELECT id WHERE age+1=10,任何对列的操作都将导致表扫描,它包括数据库教程函数、计算表达式等等,查询时要尽可能将操作移至等号右边
3.sql 语句尽可能简单:一条 sql 只能在一个 cpu 运算;大语句拆小语句,减少锁时间;一条大sql 可以堵死整个库。其次,mysql在服务层有查询缓存的功能,可以将未修改的小表的查询sql结果缓存住。
4.OR 改写成 IN:OR 的效率是 n 级别, IN 的效率是 log(n) 级别,IN 的个数建议控制在 200 以内
5.避免 %xxx 式查询,因为前缀未知的情况下无法使用索引
6.尽量避免在 WHERE 子句中使用 != 或 <> 操作符,否则将引擎放弃使用索引而进行全表扫描
7.列表数据不要拿全表,要使用 LIMIT 来分页,每页数量也不要太大
8.使用JOIN时记住小表为驱动表即主表,大表为被驱动表。千万不要背口诀“小表在前,大表在后”,因为对于left join 和 right join 主表位置不一样,千万不要背口诀。