MYSQL who are my JOINS 似乎使查询更快?

Posted

技术标签:

【中文标题】MYSQL who are my JOINS 似乎使查询更快?【英文标题】:MYSQL who are my JOINS appear to make a query faster? 【发布时间】:2021-12-14 15:33:18 【问题描述】:

我正在尝试使用“物化视图”来优化远离联接的查询性能。下面的第一个查询是原始查询,它使用连接。第二个是针对我生成的表编写的查询,该表包括所有连接数据(相当于物化视图)。它们都返回相同的结果集。不幸的是,不知何故,第二个查询在处理一组很长的输入 ID(IN 子句)时要慢得多。我不明白这怎么可能!!!!执行所有连接必须有相当数量的过热,这可以通过“物化视图”来保存,对吧?

SELECT 
        clinical_sample.INTERNAL_ID AS "internalId",
        sample.STABLE_ID AS "sampleId",
        patient.STABLE_ID AS "patientId",
        clinical_sample.ATTR_ID AS "attrId",
        cancer_study.CANCER_STUDY_IDENTIFIER AS "studyId", 
        clinical_sample.ATTR_VALUE AS "attrValue"
         
        FROM clinical_sample
        INNER JOIN sample ON clinical_sample.INTERNAL_ID = sample.INTERNAL_ID
        INNER JOIN patient ON sample.PATIENT_ID = patient.INTERNAL_ID
        INNER JOIN cancer_study ON patient.CANCER_STUDY_ID = 
                              cancer_study.CANCER_STUDY_ID
         WHERE cancer_study.CANCER_STUDY_IDENTIFIER = 'xxxxx' 
         AND  sample.STABLE_ID IN
                     ('P-0068343-T02-IM7' , 'P-0068353-T01-IM7' ,
                      'P-0068363-T01-IM7' , 'P-0068364-T01-IM7'  )
         AND clinical_sample.ATTR_ID IN
                (
                    'CANCER_TYPE'
                );
SELECT   
        internalId,
        sampleId,
      patientId,
       attrId,
        studyId, 
        attrValue
         
        FROM test
         WHERE 
         sampleId IN ('P-0068343-T02-IM7' , 'P-0068353-T01-IM7' ,
                      'P-0068363-T01-IM7' , 'P-0068364-T01-IM7'  )
         AND studyId = 'xxxxx' 
         AND attrId = 'CANCER_TYPE';

更新:我确实在 Workbench 报告中注意到,带有连接的查询似乎扫描的行数要少得多。第二个无连接查询大约为 829k 与 ~2400k。因此,以某种方式,加入似乎实际上是一项重大优化。我在 sampleId、studyId、attrId 和这三者的复合中都有索引。 表“test”和“clinical_sample”的行数相同。

【问题讨论】:

(studyId, attrId, sampleId) 上的复合索引添加到test 表中。 感谢@Barmar,它已经拥有该索引。也是列上的单个索引。我确实在 Workbench 中注意到,带有连接的查询似乎扫描的行数要少得多。第一个约为 829k,而第一个约为 2400k。 【参考方案1】:

看看每个表的PRIMARY KEY是什么会有所帮助。

其中一些索引可能会有所帮助:

clinical_sample:  INDEX(ATTR_ID, INTERNAL_ID,  ATTR_VALUE)
sample:  INDEX(STABLE_ID, INTERNAL_ID,  PATIENT_ID)
patient:  INDEX(INTERNAL_ID,  STABLE_ID, CANCER_STUDY_ID)
cancer_study:  INDEX(CANCER_STUDY_IDENTIFIER, CANCER_STUDY_ID)

对于物化视图,我同意 Barmar 的 INDEX(studyId, attrId, sampleId)

我在 sampleId、studyId、attrId 和这三者的复合中都有索引。

让我们看看EXPLAIN。当它应该使用复合索引时,它可能表明它正在使用您的索引 (sampleId)

也将IN放在最后,而不是放在首位,无论基数如何。更准确地说,将=first 放在复合索引中。

【讨论】:

这些索引在原始表上,它们对物化视图的性能没有影响。 对。谜团在于为什么物化视图会慢得多。 @Barmar - 你怎么知道这些索引在原始表上?? 我的意思是你告诉他原始表上应该有哪些索引。但他不再使用原始表格,所以它们无关紧要。 这些索引首先会影响创建物化视图的性能,但在查询视图时它们并不重要。【参考方案2】:

深思:When and why are database joins expensive? 这让我相信带有索引的规范化表实际上可能比我的非规范化尝试(物化视图)更快。

【讨论】:

以上是关于MYSQL who are my JOINS 似乎使查询更快?的主要内容,如果未能解决你的问题,请参考以下文章

解决上传到github报错Who are you

git *** Please tell me who you are.错误

WHO ARE YOU?--writeup

提交到github报错Please tell me who you are

实验吧之who are you?(时间盲注)

i春秋who are you