Heim  >  Artikel  >  Datenbank  >  Detaillierte Erläuterung der Rolle von EXPLAIN in MySQL

Detaillierte Erläuterung der Rolle von EXPLAIN in MySQL

小云云
小云云Original
2017-12-08 11:23:291550Durchsuche

Dieser Artikel stellt hauptsächlich den relevanten Inhalt von EXPLAIN in MySQL vor, beinhaltet einige Kenntnisse über die Indizierung und hat einen gewissen Referenzwert. Ich hoffe, er kann jedem helfen.

1. MYSQL-Index

Index: Eine Datenstruktur, die MySQL dabei hilft, Daten effizient zu erhalten. Es wird zur Verbesserung der Sucheffizienz verwendet und kann mit einem Wörterbuch verglichen werden. Es kann einfach als eine sortierte und schnelle Suchdatenstruktur verstanden werden.

Die Rolle des Index: Erleichtert das Abfragen und Sortieren (das Hinzufügen eines Index wirkt sich also auf die Where-Anweisung und die Order by Sorting-Anweisung aus).

Neben Daten verwalten Datenbanken auch Datenstrukturen, die bestimmte Suchalgorithmen erfüllen und auf die Daten in irgendeiner Weise verweisen. Dies ermöglicht die Implementierung erweiterter Suchalgorithmen für diese Datenstrukturen. Diese Datenstrukturen sind Indizes.

Der Index selbst ist ebenfalls sehr groß und kann nicht vollständig im Speicher gespeichert werden, daher wird der Index häufig in Form einer Indexdatei auf der Festplatte gespeichert.

Der Index, auf den wir uns normalerweise beziehen, ist im Allgemeinen ein B-Tree-Index, sofern nicht anders angegeben. (Clusterierter Index, zusammengesetzter Index, Präfixindex und eindeutiger Index sind standardmäßig alle B+-Baum-Indizes. Zusätzlich zu B-Baum-Indizes gibt es auch Hash-Indizes.)

Vorteile:

A. Verbessern Sie die Effizienz des Datenabrufs und reduzieren Sie die Datenbank-IO-Kosten
B. Durch Indexspaltenpaarung data reduziert die Datensortierungskosten und den CPU-Verbrauch.

Nachteile:

A. Der Index ist auch eine Tabelle, in der der Primärschlüssel und die Indexfelder gespeichert sind und auf die Entitätstabellendatensätze, daher nimmt auch der Index Platz ein.
B. Wenn INSERT-, UPDATE- und DELETE-Operationen für die Tabelle ausgeführt werden, aktualisiert MYSQL nicht nur die Daten, sondern speichert auch die entsprechenden Informationen der Indexspaltenfelder, die der Indexdatei bei jeder Aktualisierung hinzugefügt werden.

In der tatsächlichen Produktionsumgebung müssen wir Schritt für Schritt analysieren, den optimalen Index optimieren und festlegen sowie unsere Abfragebedingungen optimieren.

Klassifizierung von Indizes:

1. Einzelwertindex Ein Index enthält nur ein Feld und eine Tabelle kann mehrere einspaltige Indizes haben.
2. Eindeutiger Index Der Wert der Indexspalte muss eindeutig sein, es sind jedoch Nullwerte zulässig.
3. Zusammengesetzter Index: Ein Index enthält mehrere Spalten

Es wird empfohlen, weniger als 5 Indizes für eine Tabelle zu erstellen

Syntax:

1. CREATE [UNIQUE] INDEX indexName ON myTable (columnName(length));
2. ALTER myTable Add [UNIQUE] INDEX [indexName] ON (columnName(length));

Löschen: DROP INDEX [indexName] ON myTable;

Ansicht: SHOW INDEX FROM table_nameG;

2

ERKLÄREN: Simulieren Sie, wie der MySQL-Optimierer SQL-Abfrageanweisungen ausführt, damit Sie wissen, wie MySQL Ihre SQL-Anweisungen verarbeitet. Analysieren Sie die Leistungsengpässe Ihrer Abfrageanweisungen oder Tabellenstrukturen.

mysql> explain select * from tb_user;
+----+-------------+---------+------+---------------+------+---------+------+------+-------+
| id | select_type | table  | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+---------+------+---------------+------+---------+------+------+-------+
| 1 | SIMPLE   | tb_user | ALL | NULL     | NULL | NULL  | NULL |  1 | NULL |
+----+-------------+---------+------+---------------+------+---------+------+------+-------+

(1) ID-Spalte:

(1), ID gleiche Ausführungsreihenfolge von oben nach unten Weiter

mysql> explain 
  -> SELECT*FROM tb_order tb1
  -> LEFT JOIN tb_product tb2 ON tb1.tb_product_id = tb2.id
  -> LEFT JOIN tb_user tb3 ON tb1.tb_user_id = tb3.id;
+----+-------------+-------+--------+---------------+---------+---------+---------------------------+------+-------+
| id | select_type | table | type  | possible_keys | key   | key_len | ref            | rows | Extra |
+----+-------------+-------+--------+---------------+---------+---------+---------------------------+------+-------+
| 1 | SIMPLE   | tb1  | ALL  | NULL     | NULL  | NULL  | NULL           |  1 | NULL |
| 1 | SIMPLE   | tb2  | eq_ref | PRIMARY    | PRIMARY | 4    | product.tb1.tb_product_id |  1 | NULL |
| 1 | SIMPLE   | tb3  | eq_ref | PRIMARY    | PRIMARY | 4    | product.tb1.tb_user_id  |  1 | NULL |
+----+-------------+-------+--------+---------------+---------+---------+---------------------------+------+-------+

(2) Wenn es sich um eine Unterabfrage handelt, erhöht sich die ID-Seriennummer automatisch Priorität umsetzen.

mysql> EXPLAIN
  -> select * from tb_product tb1 where tb1.id = (select tb_product_id from tb_order tb2 where id = tb2.id =1);
+----+-------------+-------+-------+---------------+---------+---------+-------+------+-------------+
| id | select_type | table | type | possible_keys | key   | key_len | ref  | rows | Extra    |
+----+-------------+-------+-------+---------------+---------+---------+-------+------+-------------+
| 1 | PRIMARY   | tb1  | const | PRIMARY    | PRIMARY | 4    | const |  1 | NULL    |
| 2 | SUBQUERY  | tb2  | ALL  | NULL     | NULL  | NULL  | NULL |  1 | Using where |
+----+-------------+-------+-------+---------------+---------+---------+-------+------+-------------+

(3) Gleiche und unterschiedliche IDs existieren gleichzeitig

mysql> EXPLAIN 
  -> select * from(select * from tb_order tb1 where tb1.id =1) s1,tb_user tb2 where s1.tb_user_id = tb2.id;
+----+-------------+------------+--------+---------------+---------+---------+-------+------+-------+
| id | select_type | table   | type  | possible_keys | key   | key_len | ref  | rows | Extra |
+----+-------------+------------+--------+---------------+---------+---------+-------+------+-------+
| 1 | PRIMARY   | <derived2> | system | NULL     | NULL  | NULL  | NULL |  1 | NULL |
| 1 | PRIMARY   | tb2    | const | PRIMARY    | PRIMARY | 4    | const |  1 | NULL |
| 2 | DERIVED   | tb1    | const | PRIMARY    | PRIMARY | 4    | const |  1 | NULL |
+----+-------------+------------+--------+---------------+---------+---------+-------+------+-------+

abgeleitet2: Abgeleitete Tabelle 2 bedeutet, dass die abgeleitete Tabelle tb1 mit der ID=2 ist

(2) Spalte „select_type“: Operationstyp des Datenlesevorgangs

1. EINFACH: Einfache Auswahlabfrage, SQL enthält keine Unterabfragen oder UNION.
2. PRIMÄR: Die Abfrage enthält einen komplexen Unterabfrageteil, und die äußerste Abfrage ist als PRIMÄR markiert.
3. UNTERABFRAGE: Die Unterabfrage ist in der Auswahl- oder WHERE-Liste enthalten.
4. ABGEGEBEN: In FROM The In der Liste enthaltene Unterabfragen werden als DERIVED (abgeleitete Tabelle) markiert, und MYSQL führt diese Unterabfragen rekursiv aus und fügt die Ergebnismenge in die Nullzeittabelle ein.
5. UNION: Wenn das zweite SELECT nach UNION erscheint, wird es als UNION markiert; wenn UNION in der Unterabfrage der FROM-Klausel enthalten ist, wird das äußere SELECT als DERIVED markiert
6. UNION-ERGEBNIS: Wählen Sie diese Option aus, um Ergebnisse aus der UNION-Tabelle zu erhalten

(3) Tabellenspalte: Um welche Tabelle handelt es sich in der Datenzeile

( 4) Typspalte: Zugriffstyp vom besten zum schlechtesten System > eq_ref > ref >

  1、system:表只有一条记录(等于系统表),这是const类型的特例,平时业务中不会出现。
  2、const:通过索引一次查到数据,该类型主要用于比较primary key 或者unique 索引,因为只匹配一行数据,所以很快;如果将主键置于WHERE语句后面,Mysql就能将该查询转换为一个常量。
  3、eq_ref:唯一索引扫描,对于每个索引键,表中只有一条记录与之匹配。常见于主键或者唯一索引扫描。
  4、ref:非唯一索引扫描,返回匹配某个单独值得所有行,本质上是一种索引访问,它返回所有匹配某个单独值的行,就是说它可能会找到多条符合条件的数据,所以他是查找与扫描的混合体。
  5、range:只检索给定范围的行,使用一个索引来选着行。key列显示使用了哪个索引。一般在你的WHERE 语句中出现between 、66f7a98850431fb8c0d9470a35d9d294 、in 等查询,这种给定范围扫描比全表扫描要好。因为他只需要开始于索引的某一点,而结束于另一点,不用扫描全部索引。
  6、index:FUll Index Scan 扫描遍历索引树(扫描全表的索引,从索引中获取数据)。
  7、ALL 全表扫描 从磁盘中获取数据 百万级别的数据ALL类型的数据尽量优化。

(五)possible_keys列:显示可能应用在这张表的索引,一个或者多个。查询涉及到的字段若存在索引,则该索引将被列出,但不一定被查询实际使用。

(六)keys列:实际使用到的索引。如果为NULL,则没有使用索引。查询中如果使用了覆盖索引,则该索引仅出现在key列表中。覆盖索引:select 后的 字段与我们建立索引的字段个数一致。

(七)ken_len列:表示索引中使用的字节数,可通过该列计算查询中使用的索引长度。在不损失精确性的情况下,长度越短越好。key_len 显示的值为索引字段的最大可能长度,并非实际使用长度,即key_len是根据表定义计算而得,不是通过表内检索出来的。

(八)ref列:显示索引的哪一列被使用了,如果可能的话,是一个常数。哪些列或常量被用于查找索引列上的值。

(九)rows列(每张表有多少行被优化器查询):根据表统计信息及索引选用的情况,大致估算找到所需记录需要读取的行数。

(十)Extra列:扩展属性,但是很重要的信息。

1、 Using filesort(文件排序):mysql无法按照表内既定的索引顺序进行读取。

 mysql> explain select order_number from tb_order order by order_money;
+----+-------------+----------+------+---------------+------+---------+------+------+----------------+
| id | select_type | table  | type | possible_keys | key | key_len | ref | rows | Extra     |
+----+-------------+----------+------+---------------+------+---------+------+------+----------------+
| 1 | SIMPLE   | tb_order | ALL | NULL     | NULL | NULL  | NULL |  1 | Using filesort |
+----+-------------+----------+------+---------------+------+---------+------+------+----------------+
1 row in set (0.00 sec)

说明:order_number是表内的一个唯一索引列,但是order by 没有使用该索引列排序,所以mysql使用不得不另起一列进行排序。

2、Using temporary:Mysql使用了临时表保存中间结果,常见于排序order by 和分组查询 group by。

mysql> explain select order_number from tb_order group by order_money;
+----+-------------+----------+------+---------------+------+---------+------+------+---------------------------------+
| id | select_type | table  | type | possible_keys | key | key_len | ref | rows | Extra              |
+----+-------------+----------+------+---------------+------+---------+------+------+---------------------------------+
| 1 | SIMPLE   | tb_order | ALL | NULL     | NULL | NULL  | NULL |  1 | Using temporary; Using filesort |
+----+-------------+----------+------+---------------+------+---------+------+------+---------------------------------+
1 row in set (0.00 sec)

3、Using index 表示相应的select 操作使用了覆盖索引,避免访问了表的数据行,效率不错。

如果同时出现Using where ,表明索引被用来执行索引键值的查找。

如果没有同时出现using where 表明索引用来读取数据而非执行查找动作。

mysql> explain select order_number from tb_order group by order_number;
+----+-------------+----------+-------+--------------------+--------------------+---------+------+------+-------------+
| id | select_type | table  | type | possible_keys   | key        | key_len | ref | rows | Extra    |
+----+-------------+----------+-------+--------------------+--------------------+---------+------+------+-------------+
| 1 | SIMPLE   | tb_order | index | index_order_number | index_order_number | 99   | NULL |  1 | Using index |
+----+-------------+----------+-------+--------------------+--------------------+---------+------+------+-------------+
1 row in set (0.00 sec)

4、Using where 查找

5、Using join buffer :表示当前sql使用了连接缓存。

6、impossible where :where 字句 总是false ,mysql 无法获取数据行。

7、select tables optimized away:

8、distinct:

相关推荐:

MySQL中explain的使用以及性能分析

解析MySQL中EXPLAIN命令

mysql总结之explain_PHP教程

Das obige ist der detaillierte Inhalt vonDetaillierte Erläuterung der Rolle von EXPLAIN in MySQL. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn