在我们的应用程序中,我们有一个页面向用户显示一组数据,实际上是其中的一部分。它还允许用户通过自定义字段对其进行排序。所以最后这一切都归结为这样的查询:
SELECT name, info, description FROM mytable
WHERE active = 1 -- Some filtering by indexed column
ORDER BY name LIMIT 0,50; -- Just a part of it
只要表的大小相对较小(仅在我们部门本地使用),这就可以正常工作。但现在我们必须扩展这个应用程序。让我们假设,该表有大约一百万条记录(我们希望很快就会发生)。订购会怎样?我是否理解正确,为了进行此查询,MySQL必须每次排序一百万条记录并提供一部分内容?这似乎是一项非常耗费资源的操作。
我的想法只是关闭该功能并且不允许用户选择他们的自定义排序(可能只是过滤),以便订单是自然的(按ID降序排列,我相信索引可以处理那个)。
或者有没有办法通过订购使这个查询的工作更快?
更新:
以下是我从官方MySQL developer page中读到的内容。
在某些情况下,MySQL无法使用索引来解析ORDER BY, 虽然它仍然使用索引来查找与WHERE匹配的行 条款。这些案例包括以下内容:
....
习惯的关键 获取行与ORDER BY中使用的行不同:
SELECT * FROM t1 WHERE key2 = constant ORDER BY key1;
是的,似乎mysql会遇到这样的查询问题吗?那么,我该怎么做 - 根本不使用订单部分?
答案 0 :(得分:2)
问题'这似乎是你有2个要求(在例子中)
前者可以通过在active
字段上添加索引轻松解决
后者可以通过在name
由于您在同一个查询中同时执行这两项操作,因此您需要将此组合成一个索引,以便您快速解析active
值,然后从那里获取前50个name
第
因此,我猜这样的事情会帮助你:
CREATE INDEX idx_test ON myTable (active, name)
(理论上,一如既往,请先购买!)
请记住,虽然没有免费午餐这样的东西;您需要考虑添加索引还有缺点:
SELECT * FROM ...
这样的事情时要记住这一点:你真的需要所有的字段吗?active
和name
,但从文字中我可以看出这些可能是“动态的”#39}。在这种情况下,您必须预见各种组合。从实际角度来看,这可能是不可行的,因为每个索引都会带有上述缺点,每次添加索引时,您都会再次将该列表添加到该列表中(累积)。 PS:我使用PK
来简化,但在MSSQL中,它实际上是聚集索引的字段,其实际上是相同的。我猜测MySQL的工作方式类似。
答案 1 :(得分:1)
解释您的查询,并检查它是否适用于filesort,
如果Order By没有获得任何索引,或者MYSQL优化器更喜欢避免现有的索引进行排序,那么它将与filesort一起使用。
现在,如果您正在获取文件排序,那么您应该最好避免使用ORDER BY,或者您应该创建适当的索引。
如果数据足够小,它会在内存中执行操作,否则它会在磁盘上运行。
因此您可以尝试更改变量< sort_buffer_size>同样。
答案 2 :(得分:0)
总是权衡,提高订单查询性能的一种方法是设置buffersize,然后通过查询运行订单,即时查询性能
设置sort_buffer_size = 100000; <>
如果这个尺寸进一步增加,那么性能将开始下降