为什么我的SQL查询不使用表的复合索引?

问题描述 投票:0回答:3

我有一个users表,其列如下:id(主键),typeexternal_idexternal_typecreated_atupdated_at

索引:

  • 主要(id)
  • 唯一(external_id, external_type, type)
  • 非唯一(updated_at)

以及settings表格,其列:iduser_idnamevaluecreated_atupdated_attype

索引:

  • 主要(id)
  • 唯一(user_id, name)
  • 非唯一(user_id)
  • 非唯一(updated_at)

我执行查询:

SELECT users.id, users.type, users.external_id, users.created_at, users.updated_at,

  settings.id, settings.settings_id, settings.name, settings.value, 
  settings.created_at, settings.updated_at, settings.type

FROM users

  LEFT OUTER JOIN settings on settings.user_id = users.id

WHERE users.external_id=3 and users.external_type=“Owner”

在“解释”报告中,我看到了:

  • 对于用户表,已将(external_id,external_type,type)索引标识为可能的键,但使用了[[NOT]
  • 设置表使用(用户ID,名称)索引
  • 目标

      我想优化此查询

  • 所以我想让用户表使用(external_id,external_type,type)复合索引
  • 我已经完成的调试工作:

      如果更改SELECT语句的第一行以删除users.created_at,users.updated_at,则使用索引

  • 如果我尝试向用户表添加(external_id,external_type)非唯一索引,它仍然不使用它
  • 如果我将查询的WHERE子句更改为add和users.type =“ Blah”,它将使用索引
  • 我想念什么?
  • mysql sql indexing query-optimization database-indexes
    3个回答
    0
    投票
    这将回答问题的原始版本。

    0
    投票
    不确定所使用的mysql版本。在8.0之前,mysql innodb不会保留统计信息,并且如果您的数据倾斜,则内存中的统计信息几乎无法表示数据。在您的情况下,如果统计数据表明表用户中的大多数数据具有external_id = 3和external_type ='Owner',则查询优化器可能认为表扫描是最快的,因为表上没有索引覆盖所选的列,并且如果使用索引,查询引擎需要根据索引对数据进行查找。

    0
    投票
    这是避免重复查找
    © www.soinside.com 2019 - 2024. All rights reserved.