6查询性能优化

查询优化,索引优化,表结构优化是一起进行的,不能只靠一个

“快速,精准和实现简单"三者永远只能满足其二,必须舍弃其中一个

查询性能低下的最基本的原因是访问的数据太多了
  1. 查询不需要的记录(加上limit限制)

  2. 多表关联返回所有列(只返回需要的列)

  3. select *避免

  4. 重复查询相同数据(单条数据还好)

扫描的行数与访问类型
扫描表,扫描索引,范围访问,单值访问

    慢——————————>快

使用where的方式

    快  1索引完整的where  ->  存储引擎完成

     |  2覆盖索引扫描  ->  MySQL服务器完成

    慢  3从数据库中过滤where(回表)  ->  MySQL服务器完成
重构查询方式
  1. 将复杂查询分解成单个简单查询

  2. 切分查询(分段查,用limit,id,ctime限制范围)

  3. 分解关联查询(不分页的都可以分解)

查询执行基础
查询流程概述
1MySQL客户端/服务器通信协议

"半双工”:任何时刻只能是服务器向客户端发数据,或客户端向服务器发数据,不能同时发
优点:简单快速
缺点:无法流量控制.就像是从"消防管道喝水”(因此大查询一般都是将结果存到内存,优先释放连接资源)

2查询缓存
  • 大小写敏感的哈希查找实现
  • 权限判断
3查询优化处理
  • 语法解析与预处理
    验证语法正确性
    验证权限

  • 查询优化器
    一条查询可以有很多种执行方式都返回相同的结果,优化器的作用就是找到其中最好的
    MySQL使用基于成本的优化器,采用统计信息预测
    静态优化:直接对解析树分析,完成优化(只进行一次)
    动态优化:查询上下文有关(每次查询都需要优化)
    部分优化举例:关联表顺序,等价交换规则,预估与转化常数表达式,优化count(),min()等函数,子查询优化,提前终止查询,等值传播,列表in()比较
    总结 ==> 不要自以为比优化器更聪明

  • 关联查询 —> 嵌套循环关联

  • 执行计划 —> 左侧深度优先树

  • 关联查询优化器 —> 决定多个表的关联顺序

  • 排序优化 —> 尽量避免排序,尽量走索引排序

4查询执行引擎

将生成的执行计划(一种数据结构)逐步执行

5返回客户端
  • 返回数据影响的行
  • 缓存尝试
  • 返回数据是一个增量的,逐步返回的过程,避免服务器内存占用

查询优化器的局限性

1关联子查询  —>  尤其是in()加子查询

    如:select * from film where film_id in (select film_id from actor)

2union限制  —>  无法将限制条件从外层”下推”到内层

3索引合并优化

4等值传递  —>  大in()变关联查询

5哈希关联  —>  MySQL不支持

6并行执行  —>  无法利用多核特性

7松散索引扫描  —>  跳跃索引不支持

8最大值和最小值优化  —>  max()与min()转为limit  1走索引

9在同一个表上的查询和更新  —>  不支持同一张表同时进行查询和更新

查询优化器的提示(hint)

DELAYED  —>  延迟插入数据(对于last_insert_id()失效)

STRAIGHT_JOIN  —>  固定关联顺序

FOR UPDATE 和 LOCK IN SHARE MODE  —>  显示锁

USE INDEX  —>  索引提示

==> 最好不使用任何提示,优化器会不断升级的,伴随着升级,提示反而变成的阻碍

优化特定类型查询

1优化count()查询

    count(*)忽略列信息,直接统计行信息

2优化关联查询

    确保ON或者USING子句中的列上有索引,只需要在关联顺序的第二张表上创建索引

    确保任何group by和order by表达式,只涉及到一个表中的列

3优化子查询

    尽可能用关联查询替换

4优化group by和distinct

    对关联查询分组通常使用查找表的标识列分组(就是B表的关联列,一般是id)

    关联查询的子查询没有索引

5优化limit分页

    走二级索引只查id,避免回表的无效扫描

6优化SQL_CALC_FOUND_ROWS

    加hint,不推荐

7优化union查询

    优先使用union all

8使用自定义变量

    避免重复查询刚刚更新的数据

        如:update t set lastUpdate = NOW() where id=1 and @now :=NOW();

            select @now

    统计更新和插入的数量

        如:insert on duplicate key update时可以获取具体的更新与插入的行数

总结

  1. 在数据库层面尽量不做,少做,让应用程序多做 —> 转换思想,比如提前存储相关计算值,在应用程序转换,避免函数,走索引等
  2. 尽可能快的完成需要做的事 —> 事务update…select 而不是 select…for update
  3. 某些无法优化的查询,尝试改变策略
  4. 一些没法走索引的查询,可以先建立近似值索引,通过索引过滤到一个小范围内,再通过精准匹配数据
最后编辑于
?著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 214,128评论 6 493
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,316评论 3 388
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 159,737评论 0 349
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,283评论 1 287
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,384评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,458评论 1 292
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,467评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,251评论 0 269
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,688评论 1 306
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,980评论 2 328
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,155评论 1 342
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,818评论 4 337
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,492评论 3 322
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,142评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,382评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,020评论 2 365
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,044评论 2 352