using_where, Using temporary ,using_filesort 分享
Using filsort文档中的解释:
Mysql需要额外的一次传递,以找出如何按排序顺序检索行,通过根据联接类型浏览所有行并为所有匹配where子句的行保存排序关键字和行的指针来完成排序,然后关键字被排序,并按排序顺序检索行。额外的传递是指什么?
*************************** 1. row ***************************
Table: test_filesort
Create Table: CREATE TABLE `test_filesort` (
`a` int(11) DEFAULT NULL,
`b` int(11) DEFAULT NULL,
`c` int(11) DEFAULT NULL,
KEY `a_2` (`a`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1
1 row in set (0.00 sec)
ERROR:
No query specified
Mysql> explain select * from test_filesort where a=1 order by b;
+----+-------------+---------------+------+---------------+------+---------+-------+------+-----------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+---------------+------+---------------+------+---------+-------+------+-----------------------------+
| 1 | SIMPLE | test_filesort | ref | a_2 | a_2 | 5 | const | 1 | Using where; Using filesort |
+----+-------------+---------------+------+---------------+------+---------+-------+------+-----------------------------+
1 row in set (0.00 sec)
Mysql> alter table test_filesort add index(a,b);
Query OK, 6 rows affected (0.04 sec)
Records: 6 Duplicates: 0 Warnings: 0
Mysql> explain select * from test_filesort where a=1 order by b;
+----+-------------+---------------+------+---------------+------+---------+-------+------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+---------------+------+---------------+------+---------+-------+------+-------------+
| 1 | SIMPLE | test_filesort | ref | a_2,a | a | 5 | const | 1 | Using where |
+----+-------------+---------------+------+---------------+------+---------+-------+------+-------------+
1 row in set (0.00 sec)
额外传递指的是多做了一次排序,很少人会把所有需要排序的字段都放到索引中,出现Using filesort不一定就会有什么性能问题。当然,我是希望尽量在应用中实现order by排序,如果放在数据库这边实现,查询次数又非常大的话,尽量考虑把字段直接冗余到索引中去,避免Mysql自身的排序机制可能会引起的性能下降。
1.order by时可能会出现Using filesort。
2.order by b,如果b列不在索引中,不管b值是否相同,总会出现Using filesort。
3.并不是说所有的索引都可以避免Using filesort,hash索引是不按顺序来保存数据的。
1.如果order by 没有利用到索引,那么将会出现fileSort,如果sort_buffer不够大,fileSort过程则需要使用临时文件,fileSort优化,主要通过调整环境来达到,如下
2.设置参数,优化order by 时可能出现的file sort:
将sort_buffer_size = 1M read_rnd_buffer_size = 1M
修改为sort_buffer_size = 16M read_rnd_buffer_size = 16M
避免order by 过程 进行fileSort排序过程临时文件的产生。从3秒->0.7秒左右
参考:MySQL Order By实现原理分析和Filesort优化
3. 优化Filesort
当无法避免排序操作时,又该如何来优化呢?很显然,应该尽可能让 MySQL 选择使用第二种单路算法来进行排序。这样可以减少大量的随机IO操作,很大幅度地提高排序工作的效率。
1. 加大 max_length_for_sort_data 参数的设置
在 MySQL 中,决定使用老式排序算法还是改进版排序算法是通过参数 max_length_for_ sort_data 来决定的。当所有返回字段的最大长度小于这个参数值时,MySQL 就会选择改进后的排序算法,反之,则选择老式的算法。所以,如果有充足的内存让MySQL 存放须要返回的非排序字段,就可以加大这个参数的值来让 MySQL 选择使用改进版的排序算法。
2. 去掉不必要的返回字段
当内存不是很充裕时,不能简单地通过强行加大上面的参数来强迫 MySQL 去使用改进版的排序算法,否则可能会造成 MySQL 不得不将数据分成很多段,然后进行排序,这样可能会得不偿失。此时就须要去掉不必要的返回字段,让返回结果长度适应 max_length_for_sort_data 参数的限制。
3. 增大 sort_buffer_size 参数设置
增大 sort_buffer_size 并不是为了让 MySQL选择改进版的排序算法,而是为了让MySQL尽量减少在排序过程中对须要排序的数据进行分段,因为分段会造成 MySQL 不得不使用临时表来进行交换排序。
注:
key:显示Mysql实际决定使用的索引
Using index:只从索引中检索数据,不回表
key_len:显示Mysql决定使用的键长度
rows:显示Mysql认为它执行查询时必须检查的行数
ref:使用哪个列或常数与key一起从表中选择行
possible_keys:指出Mysql可以使用哪个索引在该表中找到行
网上案例分析:
MySQL 数据库,MyISAM 类型的表 table_item,有 5、6 个字段,主键是 id。
user_id 和 item_id 两个字段都是单独的 INDEX 类型的索引。
问题是如何发现的?
在自己的开发环境下,打开一个简单的页面都要好长时间,不知道问题出在哪里,只发现硬盘灯闪个不停。
观察 Windows 的任务管理器,看到 mysqld-nt.exe 这个进程的 "I/O 读取字节" 高达十几 G!!!
再次测试,发现每次刷新页面,这个进程要读取几十 M 的数据。
奇了怪了,查看 SQL 语句,还有表结构,字段都建了索引了呀。
后来 EXPLAIN 了一下,看到结果是 Using where; Using filesort。
explain SELECT * FROM table_item WHERE user_id = 2 ORDER BY item_id LIMIT 0, 5
翻了 MySQL 手册,仔细看下 filesort 的说明,知道了 Using filesort 是一种速度很慢的外部排序。
不过我不理解为什么会使用 filesort 排序,WHERE 和 ORDER BY 用到的字段都是有索引的呀。
赶紧 Google之,得到的启示就是索引定义不当导致MySQL 没有用到索引。
需要了解MySQL 的特性:
1.一条 SQL 语句只能使用 1 个索引 (5.0-)[5.0+MYSQ会分析是否做index megre],MySQL 根据表的状态,选择一个它认为最好的索引用于优化查询【use index 指定索引,纠正MYSQL错误判断】
2.联合索引,只能按从左到右的顺序依次使用,包括了group order
3.从上边可以看到结合索引,也可以叫多列索引,形如 key ('B1','B2','B3' ,'B4')等的,排序的思路通常为,先按照B1来排序,B1相同,然后按照B2排序,以此类推,这样对于(B1),(B1,B2), (B1,B2,B3)的索引都是有效的,可是对于(B2,B3)这样的索引就无效了。
根据这个特性就可以解决问题:
user_id 和 item_id 是 2 个索引,我的语句中,MySQL 选择了 user_id,那么 item_id 的索引没有起到任何用处,所以,当我要排序的时候,由于user_id索引取得的记录数较多,内存中的排序 buffer 满了,只能 Using filesort 进行外部排序,因此每次查询要从磁盘读取几十 M 的数据,太慢了。
修改表结构,删除 user_id 和 item_id 的 INDEX 索引,建立一个名为 user_item 的联合 UNIQUE 索引,顺序是先 user_id 后 item_id,再 EXPLAIN,这回只有 Using where 了。
再刷新页面,观察任务管理器,mysqld-nt.exe 只读取了 2K 的数据,页面咔的一下就出来了……
using_where, Using temporary ,using_filesort 分享的更多相关文章
- iOS之ShareSDK实现分享、第三方登录等功能
(1)官方下载ShareSDK iOS 2.8.8,地址:http://sharesdk.cn/ (2)根据实际情况,引入相关的库,参考官方文档. (3)在项目的AppDelegate中一般情况下有三 ...
- iOS开发---集成ShareSDK实现第三方登录、分享、关注等功能。
(1)官方下载ShareSDK IOS 2.9.6,地址:http://sharesdk.mob.com/Download (2)根据实际情况,引入相关的库,参考官方文档. (3)在项目的AppDel ...
- IOS项目集成ShareSDK实现第三方登录、分享、关注等功能。
(1)官方下载ShareSDK iOS 2.8.8,地址:http://sharesdk.cn/ (2)根据实际情况,引入相关的库,参考官方文档. (3)在项目的AppDelegate中一般情况下有三 ...
- IOS项目集成ShareSDK实现第三方登录、分享、关注等功能(备用)
(1)官方下载ShareSDK iOS 2.8.8,地址:http://sharesdk.cn/ (2)根据实际情况,引入相关的库,参考官方文档. (3)在项目的AppDelegate中一般情况下有三 ...
- iOS开发之第三方分享QQ分享,史上最新最全第三方分享QQ方式实现
本文章源码地址: https://github.com/zhonggaorong/QQLoginDemo 项目搭建参考: (包含QQ登录源码下载 . QQ sdk集成) http://blog.cs ...
- 淘宝内部分享:怎么跳出MySQL的10个大坑
编者按:淘宝自从2010开始规模使用MySQL,替换了之前商品.交易.用户等原基于IOE方案的核心数据库,目前已部署数千台规模.同时和Oracle, Percona, Mariadb等上游厂商有良好合 ...
- 每周分享之 二 http协议(2)
本次分享http协议,共分为三部分,这是第二部分,主要讲解请求与响应的字段,以及状态码. 以http/1.1版本的一个完整的请求与响应作为例子 http请求信息由三部分组成 1.请求方法(GET/PO ...
- iOS ShareSDK 三方分享/登录使用
原文 http://www.cnblogs.com/CoderAlex/p/4860352.html 一: 快速集成 1.前言 作为现在App里必不可少的用户分享需要,社交化分享显然是我们开发app里 ...
- 沉淀,再出发——在Ubuntu Kylin15.04中配置Hadoop单机/伪分布式系统经验分享
在Ubuntu Kylin15.04中配置Hadoop单机/伪分布式系统经验分享 一.工作准备 首先,明确工作的重心,在Ubuntu Kylin15.04中配置Hadoop集群,这里我是用的双系统中的 ...
随机推荐
- HDU 2586 How far away ?(LCA模板 近期公共祖先啊)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2586 Problem Description There are n houses in the vi ...
- android性能測试systrace
一:简单介绍 systrace 是 Android4.1 引入的一套用于做性能分析的工具. 基于 Linux 内核的 ftrace 机制(用于跟踪 Linux 内核的函数调用), 能够输出各个线程当前 ...
- hdu5355 Cake
Problem Description There are m soda and today is their birthday. The 1-st soda has prepared n cakes ...
- BPM使用ligerUI实现主从表显示
先看一下效果图: 界面有待美化,嘿嘿,下面说一下实现过程,当然,我的代码可能不对,就比如后台给前端返回JSON对象,应该包括状态和消息和数据,我这里直接给返回了JSON对象,所以,如果有大神,您知道怎 ...
- docker应用栈实践-nginx处理静态文件
在我的djangoweb应用在docker搭建好之后,发现一些css静态文件返回没有content-type属性,导致浏览器log一堆警告,强迫症的我受不了这一情况 目前的应用栈结构图: 一共四个容器 ...
- Splay树
class SplayNode { public: SplayNode *child[]; char value; int size; bool flip; SplayNode(), flip(fal ...
- Python 之 基础知识(五)
一.变量 1.引用 id() 函数传参 与 返回值 都是传递保存的数据的引用 2.可变和不可变类型(变量的引用地址只在赋值语句后变化) 不可变类型 内存中的数据不允许被修改 数字类型 int,bool ...
- salt-master迁移
1.在迁移到的目标机器上先安装salt-master 2.把原master机器上的/etc/salt/pki目录打包发送到迁移的机器上的同等目录下面 3.在原master机器上批量修改minion的配 ...
- RxSwift の Observable とは何か
Qiita にあげていた記事ですが.ここにもバックアップをとっておきます この記事は.2017/09/15〜17 に早稲田大学 理工学部 西早稲田キャンパスで開催される iOSDC Japan 201 ...
- 如何在CorelDRAW中创建对象阴影
阴影工具可以为对象创建光线映射的阴影效果,使对象产生较强的立体感.可以为大多数对象或群组对象添加阴影,其中包括美术字.段落文本和位图.创建对象阴影可以增加视觉层次,使图形更加逼真. CorelDRAW ...