慢MySQL SELECT查询

时间:2012-04-23 16:22:42

标签: mysql select civicrm

我的MySQL SELECT查询速度很慢,我似乎无法排除故障。

这是一个简单的,在一张有600,000条记录的桌子上。

SELECT * 
FROM  `civicrm_contact` contact
WHERE contact.external_identifier =123456

Select查询需要3-6秒之间的任何时间,这使得导入依赖于此查询的另外600,000条记录完全不切实际。

表索引显示在附加图像中:Table Indexes

如果我基于contact.id = 123456进行搜索,则查询时间将降至约0.004秒。 contact.id是表中的主键。 external_identifier是一个唯一索引。

4 个答案:

答案 0 :(得分:1)

我知道这是一个老线程,但因为它与CiviCRM有关,我以为我会推出我的想法。修复实际上不是最佳实践,因为您已更改其中一个核心打包表以使查询运行得更快。虽然这可能对你没问题,但我绝对不会向所有人推荐这个。

您的解决方案可能突出显示了查询的问题,但似乎您告诉查询您期望的数字,但实际上数据存储为VARCHAR。所以我认为简单地用单引号括起来就可以了吗?

SELECT * 来自civicrm_contact联系人 在哪里contact.external_identifier ='123456'

如果没有这个,我很确定(已与Oracle合作多年)会发生隐式数据类型转换,因此查询无法使用INDEX。

解释计划应证明这一理论。

由于

帕尔韦兹

答案 1 :(得分:0)

您似乎使用BTREE索引。如果您未对此列执行任何范围查询(使用<><=>=),则可能需要使用基于哈希的索引。< / p>

有关详细信息,请参阅Comparison of B-Tree and Hash Indexes

请参阅here确切的语法。

答案 2 :(得分:0)

我将结构更改为使用INT类型的external_identifier而不是VARCHAR。速度增加到0.006s

我不确定这是否会产生更广泛的影响

答案 3 :(得分:0)

我怀疑数据类型转换是个问题。我想知道它是否与索引字段的大小限制有关。作为btree意味着索引键可能比散列键大得多。这有必要吗?将外部ID存储在单独的表中并根据数字ID链接它们会更好吗?

这里的问题多于答案。