我有以下查询需要优化。
SELECT count(*) AS count FROM area
INNER JOIN entity ON area.id = entity.id
INNER JOIN areacust ON area.id = areacust.id
WHERE entity.deleted=0
AND area.id > 0
删除时有索引,所有表有id。
现在,当我假设有 20 Lac(200 万)条记录时,查询需要花费大量时间才能提供结果。它在 10 到 20 秒之间。
我怎样才能进一步优化它。还有其他方法可以计数吗?
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE vtiger_crmentity ref PRIMARY,entity_deleted_idx entity_deleted_idx 4 const 729726 Using where; Using index
1 SIMPLE area eq_ref PRIMARY PRIMARY 4 area.id 1 Using index
1 SIMPLE areacust eq_ref PRIMARY PRIMARY 4 area.id 1 Using where; Using index
复合键的新解释
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE entity ref PRIMARY,entity_deleted_idx,comp_index deleted_idx 4 const 928304 Using index
1 SIMPLE area eq_ref PRIMARY PRIMARY 4 entity.id 1 Using index
1 SIMPLE areacust eq_ref PRIMARY PRIMARY 4 entity.idid 1 Using index
最佳答案
根据评论,如果您想保留查询 - 您必须为 MySQL 实例分配更多资源。我假设你使用 InnoDB 作为存储引擎,否则这个建议是无用的:
增加innodb_buffer_pool
变量的值。尽你所能地。您希望分配尽可能多的 RAM。
此外,删除deleted
列上的索引,这是没用的。它的基数太低,无法成为索引。
您可以(应该)使用的另一种“技术”是手动处理此计数。
创建包含您感兴趣的计数的表。每次更新/插入/删除实体或区域记录时 - 手动更新计数值(增加、减少)。
这样你所要做的就是查找单个表的单个记录。设置自动解决这个问题的触发器应该是微不足道的。这样您就可以在运行时处理计数,而不是浪费 I/O 和 CPU 来不断遍历数据集。
关于Mysql Count查询优化,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25244099/