Heim  >  Artikel  >  Datenbank  >  高效的MySQL分页语句的效率

高效的MySQL分页语句的效率

WBOY
WBOYOriginal
2016-06-07 15:52:331161Durchsuche

只转好文章:http://www.zhangpingyong.com/mysql-pagination-code.html PERCONA PERFORMANCE CONFERENCE 2009上,来自雅虎的几位工程师带来了一篇Efficient Pagination Using MySQL的 报告,有很多亮点,本文是在原文基础上的进一步延伸。 首先看一下分页的

只转好文章:http://www.zhangpingyong.com/mysql-pagination-code.html

 

PERCONA PERFORMANCE CONFERENCE 2009上,来自雅虎的几位工程师带来了一篇”Efficient Pagination Using MySQL“的 报告,有很多亮点,本文是在原文基础上的进一步延伸。
首先看一下分页的基本原理:
mysql> explain SELECT * FROM message ORDER BY id DESC LIMIT 10000, 20/G
***************** 1. row **************
id: 1
select_type: SIMPLE
table: message
type: index
possible_keys: NULL
key: PRIMARY
key_len: 4
ref: NULL
rows: 10020
Extra:
1 row in set (0.00 sec)
limit 10000,20的意思扫描满足条件的10020行,扔掉前面的10000行,返回最后的20行,问题就在这里,如果是limit 100000,100,需要扫描100100行,在一个高并发的应用里,每次查询需要扫描超过10W行,性能肯定大打折扣。文中还提到limit n性能是没问题的,因为只扫描n行。

SELECT * FROM message WHERE id > 9527 ORDER BY id ASC LIMIT 20;

SELECT * FROM message WHERE id 不管翻多少页,每次查询只扫描20行。

如果LIMIT m,n不可避免的话,要优化效率,只有尽可能的让m小一下,我们扩展前面的”clue”做法,还是SELECT * FROM message ORDER BY id DESC,按id降序分页,每页20条,当前是第10页,当前页条目id最大的是9527,最小的是9500,比如要跳到第8页,我看的SQL语句可以这 样写:
SELECT * FROM message WHERE id > 9527 ORDER BY id ASC LIMIT 20,20;
跳转到第13页:
SELECT * FROM message WHERE id 原理还是一样,记录住当前页id的最大值和最小值,计算跳转页面和当前页相对偏移,由于页面相近,这个偏移量不会很大,这样的话m值相对较小,大大减少扫 描的行数。其实传统 的limit m,n,相对的偏移一直是第一页,这样的话越翻到后面,效率越差,而上面给出的方法就没有这样的问题。
注意SQL语句里面的ASC和DESC,如果是ASC取出来的结果,显示的时候记得倒置一下。
已在60W数据总量的表中测试,效果非常明显。

Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn