这是我写的一个查询:
SELECT DISTINCT m.*, sm.*, s.*
FROM table_1 m
LEFT JOIN table_2 sm ON m.master_id = sm.master_id
INNER JOIN (
SELECT s1.*, rn.field1, d.field2, m.field3, dt.field4, gl.field5
FROM table_3 s1
LEFT JOIN table_4 rn ON s1.secondary_id = rn.secondary_id
LEFT JOIN table_5 d ON s1.trait_id = d.trait_id
LEFT JOIN table_6 m ON s1.mix_id = m.mix_id
LEFT JOIN table_7 dt ON s1.debit_id = dt.debit_id
LEFT JOIN table_8 gl ON s1.graph_id = gl.graph_id
WHERE s1.secondary_id = 26
AND s1.dimension_id = 24
AND s1.mix_id = 43
) s ON sm.spec_id = s.spec_id
WHERE m.master_id = 1
我正在针对一个非常小的表(每个表只有约 3000-5000 条记录)对其进行测试,并从我笔记本电脑上的虚拟机中获得可接受的结果(4.8 毫秒)。
我的问题/顾虑是当表变大时,整个数据库不能驻留在内存中怎么办?
显然,所有 *_id 列都有索引(无论是 s1 表中的主键列还是外键。我在 s1.secondary_id, s1.dimension_id, s1 上也有一个多列索引.mix_id
.
这是否足够,或者任何比我更精通的人都知道我是否应该使用不同的索引,或者完全使用不同的策略来进行这种查询(针对 Table1 的查询,与 Table2 的连接,以及另一个连接针对子查询)——这是最后一部分让我对可伸缩性犹豫不决。
如有任何想法,我们将不胜感激。
PS - EXPLAIN
声明我可能正在使用一个临时表(我从连接假设),但除此之外我不确定我在看什么,类型是 const
, ref
, eq_ref
等
同样,它现在可以使用非常少量的测试数据正常工作。我只是不希望它在获得生产级别的数据后逐渐停止。
谢谢
最佳答案
评论:
- MySQL 中
from
子句中的子查询会降低性能,因为它们通常是具体化的。 - 子查询的
inner join
撤消left join
因为on
子句要求键为非NULL
。 - 您应该将数字列与数字 而不是字符串 进行比较。您可能不想要单引号。
- 绝对需要
table_3(secondary_id, dimension_id, mix_id)
上的索引(其他列可能在这些列之后有用)。
关于mysql - 不确定我的 MySQL 索引策略应该是什么样子,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45851412/