【问题标题】:General questions about index and mysql关于索引和mysql的一般问题
【发布时间】:2011-06-17 15:04:41
【问题描述】:

当我使用 Mysql 时,我试图更好地理解索引。一个问题是我仍然很难确定应该使用哪种类型的索引,例如单个索引、多列索引、覆盖索引等。

我的一个问题是,是否有一个通用规则来决定使用哪种类型的索引?当我设计我的数据库布局时,在应用程序构建完成之前,我并不确切知道所有查询将被使用。对于一张表,我可以查询一个或多个字段,也可以查询它以进行报告。所以如果我像这样查询一个表:

SELECT * FROM table1 WHERE field1 = this AND field2 = that GROUP BY field3 ORDER BY field4

是否要在 field1、field3、field3 和 field4 上创建多列索引?

如果我在同一张表上有不同的查询,例如:

SELECT * FROM table1 WHERE field1 = this and field3 = that

如果我有来自第一个查询的多列索引,由于 field1 位于索引的最左侧,第二个查询是否会使用相同的索引?

我的另一个问题是mysql查找索引是否有特定的顺序?那么对于多列或覆盖索引,我是否按 where 子句的顺序添加索引?然后是 group 子句中的任何内容,然后是 order 子句中的任何内容?还是mysql会自动做这个?

抱歉所有问题,只是在这方面寻求帮助。

【问题讨论】:

    标签: mysql performance database-design indexing


    【解决方案1】:
    • 引擎

    首先,您必须决定要为给定表使用哪个引擎

    1. InnoDB 更可取(事务...),但不提供 全文 索引
    2. 如果你需要全文索引,你必须选择MyISAM

    (全文索引根据列中的单词保持索引)

    • 表格

    你必须知道 MySQL 在 join 中每个表最多只使用 一个索引。所以,不要指望 MySQL 会组合给定表的两个索引。

    • 多列

    根据查询选择列的顺序,前提是MySQL可以根据需要使用索引的top

    例如

      CREATE INDEX myindex ON mytable (col1,col2,col3)
    

    MySQL 可以使用 (col1)、(col1,col2) 和 (col1,col2,col3) 作为索引。因此,要回答您的问题,您的索引应该在

    上创建
      (field1,field3,field2,field4).
    

    因为您的两个查询需要 (field1,field3) 和 (field1,field2,field3,field4)。

    【讨论】:

    • @ring0 所以如果你在 col1,col2,col3 上有一个索引,它可以使用 col1,col1 和 col2 以及 col1,col2,col3 但它不能用于 col1,col3?您还说应该为 field1 和 field3 创建索引,这是我在示例中给出的第二个查询的答案吗?
    • @John 没错。它不能跳过索引中的列。我编辑了答案,两个查询要使用的索引位于 4 列上,但按以下顺序排列:fiedl1、field3、field2、field4(顺序对前 2 个字段很重要,而 field3/4 可能是 field4/ 3).
    • @ring0 非常感谢您的帮助。另一个问题,你有field1,field3,field2,field4。这是否意味着对于多列索引,只要首先使用最左边的字段并且在查询中使用其余字段,索引的顺序就无关紧要了吗?那么在 field1,field3,field2,field4 上有一个索引也适用于这个查询吗? SELECT * FROM table1 WHERE field1 = this AND field4 = that
    • @John 在这种情况下,只会使用第一列索引(field1),因为 MySQL 不能跳过索引中的 field3 和 field2 来到达 field4(为了性能)。如果您需要该查询为两列使用索引,则需要一个以 (field1,field4...) 开头的索引。
    • @ring0 所以这就是我感到困惑的地方,如果我为 col1,col3,col2,col4 添加索引,这对于我给出的第一个查询如何工作 SELECT * FROM table1 WHERE field1 = this and field2 = that GROUP BY field3 ORDER BY field4
    【解决方案2】:

    当我设计我的数据库布局时,在应用程序构建完成之前,我并不确切知道所有查询将被使用

    正确。在了解所有查询之前不要建立索引。可以添加、更改、更改和删除索引。事实上,优秀的设计师会随着软件使用的变化而改变索引。

    是否要在 field1、field3、field3 和 field4 上创建多列索引?

    很少。

    如果我有来自第一个查询的多列索引,由于 field1 位于索引的最左侧,第二个查询是否会使用相同的索引?

    没有。

    我的另一个问题是 mysql 查找索引是否有特定的顺序?

    没有。

    那么对于多列或覆盖索引,我应该按 where 子句的顺序添加索引吗?

    没有

    然后是 group 子句中的任何内容,然后是 order 子句中的任何内容?

    没有。

    或者mysql会自动这样做吗?

    或多或少。

    这是规则。

    1. 设计数据库。

    2. 编写查询。

    3. 查找最常见的查询。 20% 的查询完成了 80% 的工作。专注于少数需要索引的慢速查询。

    4. 仅解释最常见查询的查询执行计划。对此有一个EXPLAIN 声明。

    5. 使用真实的数据负载衡量这些查询的性能。您必须为此构建虚假数据。有些查询会很慢。索引可能有帮助。有些查询不会很慢。

    6. 现在是困难的部分。尝试不同的索引,直到 (a) 解释计划看起来最佳并且 (b) 测量的查询性能符合您的预期。

    您不能让所有个查询都快。

    您不会为所有查询建立索引。

    专注于花费 80% 时间的 20% 查询。

    【讨论】:

      猜你喜欢
      • 2011-08-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多