2.4 索引语法
1). 创建索引
CREATE [ UNIQUE | FULLTEXT ] INDEX index_name ON table_name ( index_col_name,... ) ;
2). 查看索引
SHOW INDEX FROM table_name ;
3). 删除索引
DROP INDEX index_name ON table_name ;
案例演示:
先来创建一张表 tb_user,并且查询测试数据。
create table tb_user( id int primary key auto_increment comment '主键', name varchar(50) not null comment '用户名', phone varchar(11) not null comment '手机号', email varchar(100) comment '邮箱', profession varchar(11) comment '专业', age tinyint unsigned comment '年龄', gender char(1) comment '性别 , 1: 男, 2: 女', status char(1) comment '状态', createtime datetime comment '创建时间' ) comment '系统用户表'; INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('吕布', '17799990000', '[email protected]', '软件工程', 23, '1', '6', '2001-02-02 00:00:00');
INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('曹操', '17799990001', '[email protected]', '通讯工程', 33, '1', '0', '2001-03-05 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('赵云', '17799990002', '[email protected]', '英语', 34, '1', '2', '2002-03-02 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('孙悟空', '17799990003', '[email protected]', '工程造价', 54, '1', '0', '2001-07-02 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('花木兰', '17799990004', '[email protected]', '软件工程', 23, '2', '1', '2001-04-22 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('大乔', '17799990005', '[email protected]', '舞蹈', 22, '2', '0', '2001-02-07 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('露娜', '17799990006', '[email protected]', '应用数学', 24, '2', '0', '2001-02-08 00:00:00');
INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('程咬金', '17799990007', '[email protected]', '化工', 38, '1', '5', '2001-05-23 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('项羽', '17799990008', '[email protected]', '金属材料', 43, '1', '0', '2001-09-18 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('白起', '17799990009', '[email protected]', '机械工程及其自动 化', 27, '1', '2', '2001-08-16 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('韩信', '17799990010', '[email protected]', '无机非金属材料工 程', 27, '1', '0', '2001-06-12 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('荆轲', '17799990011', '[email protected]', '会计', 29, '1', '0', '2001-05-11 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('兰陵王', '17799990012', '[email protected]', '工程造价', 44, '1', '1', '2001-04-09 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('狂铁', '17799990013', '[email protected]', '应用数学', 43, '1', '2', '2001-04-10 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('貂蝉', '17799990014', '[email protected]', '软件工程', 40, '2', '3', '2001-02-12 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('妲己', '17799990015', '[email protected]', '软件工程', 31, '2', '0', '2001-01-30 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('芈月', '17799990016', '[email protected]', '工业经济', 35, '2', '0', '2000-05-03 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('嬴政', '17799990017', '[email protected]', '化工', 38, '1', '1', '2001-08-08 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('狄仁杰', '17799990018', '[email protected]', '国际贸易', 30, '1', '0', '2007-03-12 00:00:00');
INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('安琪拉', '17799990019', '[email protected]', '城市规划', 51, '2', '0', '2001-08-15 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('典韦', '17799990020', '[email protected]', '城市规划', 52, '1', '2', '2000-04-12 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('廉颇', '17799990021', '[email protected]', '土木工程', 19, '1', '3', '2002-07-18 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('后羿', '17799990022', '[email protected]', '城市园林', 20, '1', '0', '2002-03-10 00:00:00'); INSERT INTO tb_user (name, phone, email, profession, age, gender, status, createtime) VALUES ('姜子牙', '17799990023', '[email protected]', '工程造价', 29, '1', '4', '2003-05-26 00:00:00');
表结构中插入的数据如下:
数据准备好了之后,接下来,我们就来完成如下需求:
A. name字段为姓名字段,该字段的值可能会重复,为该字段创建索引。
CREATE INDEX idx_user_name ON tb_user(name);
B. phone手机号字段的值,是非空,且唯一的,为该字段创建唯一索引。
CREATE INDEX idx_user_pro_age_sta ON tb_user(profession,age,status);
D. 为email建立合适的索引来提升查询效率。
CREATE INDEX idx_email ON tb_user(email);
完成上述的需求之后,我们再查看tb_user表的所有的索引数据。
show index from tb_user;
2.5 SQL性能分析
2.5.1 SQL执行频率
MySQL 客户端连接成功后,通过 show [session|global] status 命令可以提供服务器状态信 息。通过如下指令,可以查看当前数据库的INSERT、UPDATE、DELETE、SELECT的访问
-- session 是查看当前会话 ; -- global 是查询全局数据 ; SHOW GLOBAL STATUS LIKE 'Com_______';
Com_delete: 删除次数
Com_insert: 插入次数
Com_select: 查询次数
Com_update: 更新次数
我们可以在当前数据库再执行几次查询操作,然后再次查看执行频次,看看 Com_select 参数会不会 变化。
通过上述指令,我们可以查看到当前数据库到底是以查询为主,还是以增删改为主,从而为数据 库优化提供参考依据。 如果是以增删改为主,我们可以考虑不对其进行索引的优化。 如果是以 查询为主,那么就要考虑对数据库的索引进行优化了。
那么通过查询SQL的执行频次,我们就能够知道当前数据库到底是增删改为主,还是查询为主。那假 如说是以查询为主,我们又该如何定位针对于那些查询语句进行优化呢? 次数我们可以借助于慢查询 日志。
接下来,我们就来介绍一下MySQL中的慢查询日志。
2.5.2 慢查询日志
慢查询日志记录了所有执行时间超过指定参数(long_query_time,单位:秒,默认10秒)的所有 SQL语句的日志。
MySQL的慢查询日志默认没有开启,我们可以查看一下系统变量 slow_query_log。
如果要开启慢查询日志,需要在MySQL的配置文件(/etc/my.cnf)中配置如下信息:
# 开启MySQL慢日志查询开关
slow_query_log=1
# 设置慢日志的时间为2秒,SQL语句执行时间超过2秒,就会视为慢查询,记录慢查询日志
long_query_time=2
配置完毕之后,通过以下指令重新启动MySQL服务器进行测试,查看慢日志文件中记录的信息
1 systemctl restart mysqld
然后,再次查看开关情况,慢查询日志就已经打开了。
测试:
A. 执行如下SQL语句 :
select * from tb_user; -- 这条SQL执行效率比较高, 执行耗时 0.00sec select count(*) from tb_sku; -- 由于tb_sku表中, 预先存入了1000w的记录, count一次,耗时 13.35sec
B. 检查慢查询日志 :
最终我们发现,在慢查询日志中,只会记录执行时间超多我们预设时间(2s)的SQL,执行较快的SQL 是不会记录的。
那这样,通过慢查询日志,就可以定位出执行效率比较低的SQL,从而有针对性的进行优化。
2.5.3 profile详情
show profiles 能够在做SQL优化时帮助我们了解时间都耗费到哪里去了。通过have_profiling 参数,能够看到当前MySQL是否支持profile操作:
SELECT @@have_profiling ;
可以看到,当前MySQL是支持 profile操作的,但是开关是关闭的。可以通过set语句在 session/global级别开启profiling:
SET profiling = 1;
开关已经打开了,接下来,我们所执行的SQL语句,都会被MySQL记录,并记录执行时间消耗到哪儿去 了。 我们直接执行如下的SQL语句:
select * from tb_user; select * from tb_user where id = 1; select * from tb_user where name = '白起'; select count(*) from tb_sku;
执行一系列的业务SQL的操作,然后通过如下指令查看指令的执行耗时:
-- 查看每一条SQL的耗时基本情况 show profiles; -- 查看指定query_id的SQL语句各个阶段的耗时情况 show profile for query query_id; -- 查看指定query_id的SQL语句CPU的使用情况 show profile cpu for query query_id;
查看每一条SQL的耗时情况:
查看指定SQL各个阶段的耗时情况 :
2.5.4 explain
EXPLAIN 或者 DESC命令获取 MySQL 如何执行 SELECT 语句的信息,包括在 SELECT 语句执行 过程中表如何连接和连接的顺序。
语法:
-- 直接在select语句之前加上关键字 explain / desc EXPLAIN SELECT 字段列表 FROM 表名 WHERE 条件 ;
Explain 执行计划中各个字段的含义:
字段 |
含义 |
id |
select查询的序列号,表示查询中执行select子句或者是操作表的顺序 (id相同,执行顺序从上到下;id不同,值越大,越先执行)。 |
select_type |
表示 SELECT 的类型,常见的取值有 SIMPLE(简单表,即不使用表连接或者子查询)、PRIMARY(主查询,即外层的查询)、 UNION(UNION 中的第二个或者后面的查询语句)、 SUBQUERY(SELECT/WHERE之后包含了子查询)等 |
type |
表示连接类型,性能由好到差的连接类型为NULL、system、const、 eq_ref、ref、range、 index、all 。 |
possible_key |
显示可能应用在这张表上的索引,一个或多个。 |
key |
实际使用的索引,如果为NULL,则没有使用索引。 |
key_len |
表示索引中使用的字节数, 该值为索引字段最大可能长度,并非实际使用长度,在不损失精确性的前提下, 长度越短越好 。 |
rows |
MySQL认为必须要执行查询的行数,在innodb引擎的表中,是一个估计值,可能并不总是准确的。 |
filtered |
表示返回结果的行数占需读取行数的百分比, filtered 的值越大越好。 |
标签:status,00,name,Day3,进阶篇,user,MySQL,tb,email From: https://www.cnblogs.com/beichens/p/17438120.html