sql >> Databasteknik >  >> RDS >> Mysql

Mysql-index på vy fungerar inte

Du kan inte skapa ett index på en vy:http:/ /dev.mysql.com/doc/refman/5.7/en/view-restrictions.html , så du får hoppas att indexet används. https://stackoverflow.com/a/7922711/3595565

Lösning

Det finns en lösning som nämns i kommentarerna i en annan del av dokumentationen:https://dev.mysql.com/doc/refman/5.5/en/create-view.html Där du skapar en vanlig tabell och ställer in ditt specialiserade index och laddar data från vyn till tabellen.

LOCK TABLES materializedView WRITE; 
TRUNCATE materializedView; 
INSERT INTO materializedView SELECT * FROM regularView;
UNLOCK TABLES;

Varför använder din fråga inte indexen?

När du använder UNION i en SELECT mysql skapar en tillfällig tabell för att spara data. Så eftersom en vy är en "genväg" för din mer komplexa fråga, när du anropar select kommer den att köra föreningen igen, använd en temporär tabell... använd den frestande algoritmen för att bearbeta data.

Kontrollerar manualen igen:http://dev.mysql. com/doc/refman/5.7/en/view-restrictions.html

Slutsats :UNION i din fråga hindrar vyn från att använda indexen.

Källor

fråga i mysql-forumet för samma problem svar:

felrapport "SKAPA INTE TILLFÄLLIGA TABELLER FÖR UNION ALLA"

Fixat i MySQL 5.7 http:/ /dev.mysql.com/doc/relnotes/mysql/5.7/en/news-5-7-3.html

Några testdata för att kontrollera profileraren

CREATE TABLE test1 (
    id int auto_increment PRIMARY KEY,
  col1 varchar(50),
  col2 varchar(50)
);

CREATE TABLE test2 (
    id int auto_increment PRIMARY KEY,
  col1 varchar(50),
  col2 varchar(50)
);

INSERT INTO test1 (col1, col2) 
VALUES 
('test', 'testcol2'),
('test', 'testcol2'),
('test', 'testcol2'),
('test', 'testcol2'),
('test', 'testcol2'),
('test', 'testcol2');


INSERT INTO test2 (col1, col2) 
VALUES 
('test2', 'testcol2'),
('test2', 'testcol2'),
('test2', 'testcol2'),
('test2', 'testcol2'),
('test2', 'testcol2'),
('test2', 'testcol2');

CREATE VIEW testview AS
SELECT * FROM test1
UNION
SELECT * FROM test2;

Kontrollera profileraren:

SET PROFILING = 1;
SELECT * FROM testview WHERE id = 1;
+----+-------+----------+
| id | col1  | col2     |
+----+-------+----------+
|  1 | test  | testcol2 |
|  1 | test2 | testcol2 |
+----+-------+----------+
SHOW PROFILE;
+--------------------------------+----------+
| Status                         | Duration |
+--------------------------------+----------+
| starting                       | 0.000017 |
| Waiting for query cache lock   | 0.000004 |
| checking query cache for query | 0.000029 |
| checking permissions           | 0.000006 |
| Opening tables                 | 0.000121 |
| System lock                    | 0.000012 |
| checking permissions           | 0.000014 |
| checking permissions           | 0.000032 |
| optimizing                     | 0.000004 |
| statistics                     | 0.000007 |
| preparing                      | 0.000006 |
| executing                      | 0.000003 |
| Sending data                   | 0.000046 |
| optimizing                     | 0.000003 |
| statistics                     | 0.000004 |
| preparing                      | 0.000003 |
| executing                      | 0.000002 |
| Sending data                   | 0.000023 |
| optimizing                     | 0.000003 |
| statistics                     | 0.000003 |
| preparing                      | 0.000003 |
| executing                      | 0.000002 |
| Sending data                   | 0.000008 |
| removing tmp table             | 0.000005 |
| Sending data                   | 0.000005 |
| Waiting for query cache lock   | 0.000002 |
| Sending data                   | 0.000024 |
| init                           | 0.000011 |
| optimizing                     | 0.000006 |
| statistics                     | 0.000004 |
| preparing                      | 0.000006 |
| executing                      | 0.000002 |
| Sending data                   | 0.000021 |
| end                            | 0.000003 |
| query end                      | 0.000004 |
| closing tables                 | 0.000002 |
| removing tmp table             | 0.000004 |
| closing tables                 | 0.000006 |
| freeing items                  | 0.000005 |
| Waiting for query cache lock   | 0.000003 |
| freeing items                  | 0.000013 |
| Waiting for query cache lock   | 0.000002 |
| freeing items                  | 0.000002 |
| storing result in query cache  | 0.000003 |
| logging slow query             | 0.000002 |
| cleaning up                    | 0.000003 |
+--------------------------------+----------+

Jag kan inte ta bort för mycket information från profilen, men den nämner tillfällig tabell, tillräckligt (för mig) för att bekräfta min slutsats.




  1. Hur man sparar en färdig polygon poäng leaflet.draw till mysql-tabellen

  2. MySQL:s alternativ till T-SQL:s MED BAND

  3. Skapar ENUM-variabeltyp i MySQL

  4. Exportera poster i excel-fil