MySQL - 基本2表查询慢 - 索引在哪里?

发布于 2024-10-05 11:01:48 字数 1906 浏览 10 评论 0原文

我有一个 MySQL 5.0 查询,从网页调用,经常需要 14 秒以上,而且用户不耐烦。这相当简单,从 2 个表中选择 11 列。我有三个问题:

  1. 连接的位置重要吗?
  2. where 子句的顺序重要吗?MySQL 会优化吗?
  3. 和索引对我的情况有帮助吗?

sql:

select table1.id, table1.DateOpened, table1.Status, table2.Name, etc
from (table1 join table2 on((table1.CurrentName = table2.id))) 
where table1.Type = 'Add' and (Status = 'Open' OR Status = 'Pending');

表/列信息:

table1 has 750,000 rows, table2 1.5M rows.
indexed: table1.id, table2.id
INT columns: id, table1.CurrentName
table1.Status = always populated with 1 of 4 values, 
                maybe 300 are 'Open' or 'Pending'
table1.Type = 3 possible values: 'Add', 'Change', or null
  1. 与在 WHERE 子句中添加 'table1.CurrentName = table2.id' 相比,在 FROM 中加入 JOIN 有什么优势吗?

  2. 有 3 个 WHERE 子句(带有连接)。我用各种顺序组合运行 EXPLAIN,结果似乎是相同的。

  3. 我认为向 table1.CurrentName 添加索引可能会有所帮助,但现在我认为没有。我修改了查询以删除对 table2 的引用,但它仍然运行缓慢。 (参见 3b)

  4. 似乎大部分减速可能只是读取 800K 记录并查看类型和状态值。对只有 3 或 4 个可能值的这两列进行索引是否有意义?我认为只有当存在更多唯一值时才有意义。

解释结果:

+----+-------------+--------+--------+---------------+---------+---------+-----------------------+--------+-------------+ 
| id | select_type | table  | type   | possible_keys | key     | key_len | ref                   | rows   | Extra       |         
+----+-------------+--------+--------+---------------+---------+---------+-----------------------+--------+-------------+ 
|  1 | SIMPLE      | table1 | ALL    | CurrentName   | NULL    | NULL    | NULL                  | 733190 | Using where | 
|  1 | SIMPLE      | table2 | eq_ref | PRIMARY       | PRIMARY | 4       | db.table1.CurrentName | 1      |             | 
+----+-------------+--------+--------+---------------+---------+---------+-----------------------+--------+-------------+ 
2 rows in set (0.00 sec)

I have a MySQL 5.0 query regularly taking 14+ seconds, called from a web page, and users are impatient. It's fairly simple, selecting 11 columns from 2 tables. I have three questions:

  1. Does placement of join matter?
  2. Does order of where clause matter, or will MySQL optimize?
  3. Would and index help in my case?

sql:

select table1.id, table1.DateOpened, table1.Status, table2.Name, etc
from (table1 join table2 on((table1.CurrentName = table2.id))) 
where table1.Type = 'Add' and (Status = 'Open' OR Status = 'Pending');

table/column info:

table1 has 750,000 rows, table2 1.5M rows.
indexed: table1.id, table2.id
INT columns: id, table1.CurrentName
table1.Status = always populated with 1 of 4 values, 
                maybe 300 are 'Open' or 'Pending'
table1.Type = 3 possible values: 'Add', 'Change', or null
  1. Is there any advantage JOINing in the FROM, vs adding 'table1.CurrentName = table2.id' in the WHERE clause?

  2. There are 3 WHERE clauses (with the join). I ran EXPLAIN with various order combinations, and results seemed to be the same.

  3. I thought adding an index to table1.CurrentName may help, but now I'm thinking not. I modified the query to remove references to table2, and it still ran slow. (see 3b)

  4. Seems like the bulk of the slowdown may be just reading 800K records looking at the Type and Status values. Does it make sense to index these two columns, where there are only 3 or 4 possible values? I thought it only made sense when there were more unique values.

explain results:

+----+-------------+--------+--------+---------------+---------+---------+-----------------------+--------+-------------+ 
| id | select_type | table  | type   | possible_keys | key     | key_len | ref                   | rows   | Extra       |         
+----+-------------+--------+--------+---------------+---------+---------+-----------------------+--------+-------------+ 
|  1 | SIMPLE      | table1 | ALL    | CurrentName   | NULL    | NULL    | NULL                  | 733190 | Using where | 
|  1 | SIMPLE      | table2 | eq_ref | PRIMARY       | PRIMARY | 4       | db.table1.CurrentName | 1      |             | 
+----+-------------+--------+--------+---------------+---------+---------+-----------------------+--------+-------------+ 
2 rows in set (0.00 sec)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

格子衫的從容 2024-10-12 11:01:49

连接的位置重要吗?

它们的写入顺序对于 INNER JOIN 来说并不重要。

where 子句的顺序重要吗?MySQL 会优化吗?

不会。WHERE 子句中的写入顺序对于 MySQL 查询解析器和优化器来说并不重要

索引对我的情况有帮助吗?

有潜力。 table1 上的复合索引 type_status (Type, Status) 可能会有所帮助,因为这是 WHERE 子句可以减少初始行读取的地方。

与在 WHERE 子句中添加“table1.CurrentName = table2.id”相比,在 FROM 中进行 JOIN 有什么优势吗?

对于 INNER JOIN,JOIN 条件是否位于 FROM 子句或 WHERE 子句中并不重要。

我认为向 table1.CurrentName 添加索引可能会有所帮助,但现在我认为没有。我修改了查询以删除对 table2 的引用,但它仍然运行缓慢。 (参见 3b)

table1.CurrentName 上的索引对查询没有帮助。

似乎大部分减速可能只是读取 800K 记录并查看类型和状态值。

这强化了我上面的想法。要添加复合索引(在线可能不是一件好事),就像

ALTER TABLE table1 ADD INDEX type_status (Type, Status);

我认为只有当存在更多独特的值时才有意义。

选择性肯定有帮助,但高基数并不是唯一合适的环境。

Does placement of join matter?

The order they are written does not matter for INNER JOINs.

Does order of where clause matter, or will MySQL optimize?

No. The written order in a WHERE clause does not matter to the MySQL query parser and optimizer

Would and index help in my case?

Potentially. A compound index type_status (Type, Status) on table1 could help since that is where your WHERE clause could reduce the initial rows read.

Is there any advantage JOINing in the FROM, vs adding 'table1.CurrentName = table2.id' in the WHERE clause?

For INNER JOINs, it doesn't matter if the JOIN condition is in the FROM clause or the WHERE clause.

I thought adding an index to table1.CurrentName may help, but now I'm thinking not. I modified the query to remove references to table2, and it still ran slow. (see 3b)

An index on table1.CurrentName would not help the query.

Seems like the bulk of the slowdown may be just reading 800K records looking at the Type and Status values.

This reinforces my thought above. To add the compound index (potentially not a good thing to do online), it'd be something like

ALTER TABLE table1 ADD INDEX type_status (Type, Status);

I thought it only made sense when there were more unique values.

Selectivity definitely helps, but high cardinality is not the only suitable context.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文