一:基础数据准备

DROP TABLE IF EXISTS `tbl_user`;
CREATE TABLE `tbl_user` (
`id` int() NOT NULL AUTO_INCREMENT,
`username` varchar() DEFAULT NULL,
`email` varchar() DEFAULT NULL,
`age` tinyint() DEFAULT NULL,
`type` int() DEFAULT NULL,
`create_time` datetime DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT= DEFAULT CHARSET=utf8; INSERT INTO `tbl_user` VALUES
('', 'admin', 'admin@126.com', '', '', '2018-07-09 11:08:57'),
('', 'mengday', 'mengday@163.com', '', '', '2018-07-09 11:09:00'),
('', 'mengdee', 'mengdee@163.com', '', '', '2018-07-09 11:09:04'),
('', 'root', 'root@163.com', '', '', '2018-07-09 14:36:19'),
('', 'zhangsan', 'zhangsan@126.com', '', '', '2018-07-09 14:37:28'),
('', 'lisi', 'lisi@gmail.com', '', '', '2018-07-09 14:37:31'),
('', 'wangwu', 'wangwu@163.com', '', '', '2018-07-09 14:37:34'),
('', 'zhaoliu', 'zhaoliu@163.com', '', '', '2018-07-11 18:29:24'),
('', 'fengqi', 'fengqi@163.com', '', '', '2018-07-11 18:29:32'); DROP TABLE IF EXISTS `tbl_userinfo`;
CREATE TABLE `tbl_userinfo` (
`id` int() NOT NULL AUTO_INCREMENT,
`address` varchar() DEFAULT NULL,
`user_id` int() DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `idx_userId` (`user_id`)
) ENGINE=InnoDB AUTO_INCREMENT= DEFAULT CHARSET=utf8; INSERT INTO `tbl_userinfo` VALUES
('', '上海市', ''),
('', '北京市', ''),
('', '杭州', ''),
('', '深圳', ''),
('', '广州', ''),
('', '海南', '');

二:五百万数据插入

上面插入几条测试数据,在使用索引时还需要插入更多的数据作为测试数据,下面就通过存储过程插入500W条数据作为测试数据

-- 修改mysql默认的结束符号,默认是分号;但是在函数和存储过程中会使用到分号导致解析不正确
DELIMITER $$ -- 随机生成一个指定长度的字符串
CREATE FUNCTION rand_string(n INT) RETURNS VARCHAR()
BEGIN
# 定义三个变量
DECLARE chars_str VARCHAR() DEFAULT 'abcdefghijklmnopqrstuvwxyzABCDEFJHIJKLMNOPQRSTUVWXYZ';
DECLARE return_str VARCHAR() DEFAULT '';
DECLARE i INT DEFAULT ; WHILE i < n DO
SET return_str = CONCAT(return_str, SUBSTRING(chars_str, FLOOR(+RAND()*), ));
SET i = i + ;
END WHILE;
RETURN return_str;
END $$ -- 创建插入的存储过程
CREATE PROCEDURE insert_user(IN START INT(), IN max_num INT())
BEGIN
DECLARE i INT DEFAULT ;
SET autocommit = ;
REPEAT
SET i = i + ;
INSERT INTO tbl_user VALUES ((START+i) ,rand_string(), CONCAT(rand_string(), '@random.com'), +FLOOR(RAND()*), , NOW());
UNTIL i = max_num
END REPEAT;
COMMIT;
END $$ -- 将命令结束符修改回来
DELIMITER ; -- 调用存储过程,插入500万数据,需要等待一会时间,等待执行完成
CALL insert_user(,);
-- Query OK, rows affected ( min 49.89 sec) SELECT COUNT(*) FROM tbl_user;

三:使用索引和不使用索引的比较

使用索引之前的查询

然后给username创建索引再次查询(数据库卡死了,我用sqlyog做)

创建索引用了40秒,属实有点慢

然后再查询试试,基本是秒查了,效率提升很明显

之前再黑窗口加的索引也上去了

然后删除一个索引,byusername

四:explain命令

explain参数详解

查看索引的使用情况:show status like 'Handler_read%'

Handler_read_key: 越高越好
Handler_read_rnd_next:越低越好

查询优化器:

  • 重新定义表的关联顺序(优化器会根据统计信息来决定表的关联顺序)
  • 将外连接转化成内连接(当外连接等于内连接)
  • 使用等价变换规则(如去掉1=1)
  • 优化count()、min()、max()
  • 子查询优化
  • 提前终止查询
  • in条件优化

mysql可以通过 EXPLAIN EXTENDED 和 SHOW WARNINGS 来查看mysql优化器改写后的sql语句

下图提示我们别用*查询,应该写具体那一列

五:走索引的情况和不走索引的情况

1. in走索引

in操作能避免则避免,若实在避免不了,需要仔细评估in后边的集合元素数量,控制在1000个之内。

2. 范围查询走索引

但是条件必须是一个具体的值,如果条件为 now() 当前时间,则会导致全表扫描

3. 模糊查询只有左前缀使用索引

4. 反向条件不走索引 != 、 <> 、 NOT IN、IS NOT NULL

一个优化的实例:

# 常见的对not in的优化,使用左连接加上is null的条件过滤
SELECT id, username, age FROM tbl_user WHERE id NOT IN (SELECT user_id FROM tbl_order); SELECT u.id, u.username, u.age
FROM tbl_user u
LEFT JOIN tbl_order o ON u.id = o.user_id
WHERE o.user_id IS NULL;

5. 对条件计算(使用函数或者算数表达式)不走索引

使用函数计算不走索引,无论是对字段使用了函数还是值使用了函数都不走索引,解决办法通过应用程序计算好,将计算的结果传递给sql,而不是让数据库去计算

6. 查询时必须使用正确的数据类型

如果索引字段是字符串类型,那么查询条件的值必须使用引号,否则不走索引

7. or 使用索引和不使用索引的情况

or 只有两边都有索引才走索引,如果都没有或者只有一个是不走索引的

8. 用union少用or

尽量避免使用or,因为大部分or连接的两个条件同时都进行索引的情况几率比较小,应使用uninon代替,这样能走索引的走索引,不能走索引的就全表扫描。

9. 能用union all就不用union

union all 不去重复,union去重复,union使用了临时表,应尽量避免使用临时表

10. 复合索引

对于复合索引,如果单独使用右边的索引字段作为条件时不走索引的。即复合索引如果不满足最左原则leftmost不会走复合索引

暂未完成,更新还会继续

MYSQL调优实战的更多相关文章

  1. 数据库MySQL调优实战经验总结<转>

    数据库MySQL调优实战经验总结 MySQL 数据库的使用是非常的广泛,稳定性和安全性也非常好,经历了无数大小公司的验证.仅能够安装使用是远远不够的,MySQL 在使用中需要进行不断的调整参数或优化设 ...

  2. 数据库MySQL调优实战经验总结

    MySQL 数据库的使用是非常的广泛,稳定性和安全性也非常好,经历了无数大小公司的验证.仅能够安装使用是远远不够的,MySQL 在使用中需要进行不断的调整参数或优化设置,才能够发挥 MySQL 的最大 ...

  3. Java虚拟机性能监控与调优实战

    From:  https://c.m.163.com/news/a/D7B0C6Q40511PFUO.html?spss=newsapp&fromhistory=1 Java虚拟机性能监控与调 ...

  4. MySQL 调优/优化的 100 个建议

    MySQL 调优/优化的 100 个建议   MySQL是一个强大的开源数据库.随着MySQL上的应用越来越多,MySQL逐渐遇到了瓶颈.这里提供 101 条优化 MySQL 的建议.有些技巧适合特定 ...

  5. MySQL 调优基础(一) CPU与进程

    一般而言,MySQL 的调优可以分为两个层面,一个是在MySQL层面上进行的调优,比如SQL改写,索引的添加,MySQL各种参数的配置:另一个层面是从操作系统的层面和硬件的层面来进行调优.操作系统的层 ...

  6. MySQL调优系列基础篇

    前言 有一段时间没有写博客了,整天都在忙,上班,录制课程,恰巧最近一段时间比较清闲,打算弄弄MYSQL数据库. 关于MySQL数据库,这里就不做过多的介绍,开源.免费等特性深受各个互联网行业喜爱,尤其 ...

  7. JVM 性能调优实战之:一次系统性能瓶颈的寻找过程

    玩过性能优化的朋友都清楚,性能优化的关键并不在于怎么进行优化,而在于怎么找到当前系统的性能瓶颈.性能优化分为好几个层次,比如系统层次.算法层次.代码层次…JVM 的性能优化被认为是底层优化,门槛较高, ...

  8. JVM 性能调优实战之:使用阿里开源工具 TProfiler 在海量业务代码中精确定位性能代码

    本文是<JVM 性能调优实战之:一次系统性能瓶颈的寻找过程> 的后续篇,该篇介绍了如何使用 JDK 自身提供的工具进行 JVM 调优将 TPS 由 2.5 提升到 20 (提升了 7 倍) ...

  9. mysql调优 基础

    MySQL调优可以从几个方面来做: 1. 架构层:做从库,实现读写分离: 2.系统层次:增加内存:给磁盘做raid0或者raid5以增加磁盘的读写速度:可以重新挂载磁盘,并加上noatime参数,这样 ...

随机推荐

  1. ROS 用 roboware实现节点信息发送和接收

    在ros下实现节点编程,实现一个节点发送消息,另一个节点接收.实现方式有多种,可以直接在命令窗口创建工作空间包以及节点,用catkin_make进行编译,添加.bash路径,然后执行rosrun  p ...

  2. Open Source GIS and Freeware GIS Applications

    Open Source GIS and Freeware GIS Applications   An open source application by definition is software ...

  3. 为更强大而生的开源关系型数据库来了!阿里云RDS for MySQL 8.0 正式上线!

    2019年5月29日15时,阿里云RDS for MySQL 8.0正式上线,使得阿里云成为紧跟社区步伐,发布MySQL最新版本的云厂商.RDS for MySQL 8.0 产品是阿里云推出的 MyS ...

  4. Git Commit Message 规范

    今天来说说团队开发中,对于 Git commit message 规范问题. 社区上有各种 Commit message 的规范,本文介绍 Angular 规范,目前使用较广,比较合理和系统化,并且有 ...

  5. ras 加解密类,支持截取

    class RsaEncrypt{ private $_privateKey = false; private $_publicKey = false; /** * 私钥解密 * @param $da ...

  6. 使用colab平台进行训练

    https://www.zhongxiaoping.cn/2018/12/01/%E4%BD%BF%E7%94%A8colab%E5%B9%B3%E5%8F%B0%E8%BF%9B%E8%A1%8C% ...

  7. springboot2.04与activiti 6.0集成

    本文就不对activiti做解释,下面直接看项目集成 以下顺序方面根据我的理解来,可以先从第二章看,再看第一张与第三章 增加activiti表的API,备注用. 目录 一.springboot2.X集 ...

  8. 【t065】最敏捷的机器人

    Time Limit: 1 second Memory Limit: 128 MB [问题描述] [背景] Wind设计了很多机器人.但是它们都认为自己是最强的,于是,一场比赛开始了~ [问题描述] ...

  9. 2019-10-10-优雅调试-REST-API-的工具

    title author date CreateTime categories 优雅调试 REST API 的工具 lindexi 2019-10-10 20:9:33 +0800 2019-10-1 ...

  10. P1036 最大公约数

    题目描述 给你两个正整数A和B,求它们的最大公约数. 输入格式 两个正整数 \(A,B(1 \le A,B \le 10^9)\) . 输出格式 一个整数,表示A和B的最大公约数. 样例输入 6 8 ...