如何避免花时间在 MySQL 中创建 tmp 表
Posted
技术标签:
【中文标题】如何避免花时间在 MySQL 中创建 tmp 表【英文标题】:How to avoid spending time in creating tmp table in MySQL 【发布时间】:2015-06-25 16:56:23 【问题描述】:我有以下 mysql 查询。
SELECT
COUNT(analyzer_host.server) AS count,
analyzer_host.server AS server
FROM
analyzer_host,
analyzer_url,
analyzer_code
WHERE
analyzer_host.server IS NOT NULL
AND analyzer_host.server != ''
AND analyzer_code.account_id = 33
AND analyzer_code.id = analyzer_url.url_id
AND analyzer_url.id = analyzer_host.url_id
GROUP BY analyzer_host.server;
我对此查询进行了一些分析,这被困在 "Copying to tmp table" 中。有没有办法可以避免这种情况。还有导致查询创建 tmp 表的任何指针。
【问题讨论】:
为什么要按同一个字段进行分组和计数?如果您想要每个服务器的所有记录,只需使用 COUNT(*) 需要分组,因为稍后我将使用该信息计算应用程序中每个服务器的百分比。 是否在analyzer_host.server
列上创建了索引?这个索引对于MySql进行group by
优化至关重要,阅读这个链接:dev.mysql.com/doc/refman/5.7/en/group-by-optimization.html
是的,但它也是与其他列的复合索引的一部分。
请停止使用隐式语法。这是一种 SQL 反模式,您应该在 20 多年前就停止使用它。
【参考方案1】:
第一
SELECT COUNT(host.server) AS count, host.server AS server
FROM host
JOIN url ON url.id = host.url_id
JOIN code ON code.id = url.url_id
WHERE host.server IS NOT NULL
AND host.server != ''
AND code.account_id = 33
GROUP BY host.server;
这摆脱了analyzer_
的混乱并使用JOIN...ON
语法。
其次,JOIN 似乎不太正确——url
中是否同时存在 id
和 url_id
? url_id
在host
和url
之间有区别吗?
code
有 PRIMARY KEY(account_id)
吗?这就是优化器希望开始的地方。
请提供EXPLAIN SELECT ...
,以便我们查看它是否正在执行任何表扫描。如果是,那么 那个 是问题所在,而不是“tmp 表”。
如果您需要进一步讨论,请为所有三个表格提供SHOW CREATE TABLE
。
【讨论】:
以上是关于如何避免花时间在 MySQL 中创建 tmp 表的主要内容,如果未能解决你的问题,请参考以下文章
pyspark 给出以下错误无法在 /tmp 中创建本地目录
发布 AWS Amplify GraphQL 突变时如何避免在数组中创建重复项
使用聚合操作时如何避免在 data.table 中创建重复项