Her er dine spørgsmål. Flertal. Ved at omformulere dem (med "med andre ord") er de blot forskellige spørgsmål. At gøre det gør det ikke nødvendigvis nemmere for respondenterne. Tværtimod.
Q1:[Titelspørgsmål] Betyder jokertegn i kolonnen længst til venstre i det sammensatte indeks, at resterende kolonner i indekset ikke bruges i indeksopslag (MySQL)?
A1:Nej, det betyder ikke det.
Spørgsmål 2:Betyder jokertegnet, der bruges i last_name-tilstanden, at first_name-betingelsen ikke vil blive brugt til yderligere at hjælpe MySQL med at finde indekser?
A2:Nej, det betyder det ikke. Plus halen af det spørgsmål er tvetydig. Den ved allerede, hvilket indeks, der skal bruges, kunne være et udløbersvar på en sådan vaghed.
Spørgsmål 3:Med andre ord, ved at sætte et jokertegn på efternavn-betingelsen vil MySQL kun lave et delvist indeksopslag (og ignorerer betingelser givet i kolonnerne, der er til højre for efternavn)?
A3:Nej. Kolonnerne længst til højre serveres fra indekset svarende til en dækkende indeksstrategi, der drager fordel af det langsomme datasideopslag.
Q4:... ville Eksempel-1 være hurtigere end Eksempel-2?
A4:Ja. Det er et dækkende indeks med hensyn til disse kolonner. Se dækkende indekser.
Som en sidebemærkning vedrørende Q4. Det er irrelevant, om det er en PK eller ikke-PK. Der er sikkert et dusin grunde til, at det som PK ville være forfærdeligt for din ansøgning.
Originale svar nedenfor:
med kun en sammensat nøgle på (last_name,first_name)
og en forespørgsel som du nævner
WHERE first_name LIKE 'joh%'
... Den vil slet ikke bruge indekset. Det vil lave en tabelscanning. På grund af fraværet af
- en enkelt kolonnenøgle på
first_name
- en sammensat nøgle med
first_name
længst til venstre
Så bordscanning her kommer vi.
Se venligst manualsiden Multiple-Column Indexes a> at læse mere. Og fokuser på left-most
begrebet det. Faktisk, gå til den side og søg på ordet left
.
Se manualsiden på Forklar facilitet i mysql. Også artiklen Brug Explain til at skrive bedre Mysql-forespørgsler .
Rediger
Der har været et par redigeringer af spørgsmålet, siden jeg var her for en time eller to siden. Jeg vil efterlade dig med følgende. Kør din faktiske forespørgsel gennem forklaring, og dechifrer gennem Using Explain ...
link ovenfor eller en anden reference
drop table myNames;
create table myNames
( id int auto_increment primary key,
lastname varchar(100) not null,
firstname varchar(100) not null,
col4 int not null,
key(lastname,firstname)
);
truncate table myNames;
insert myNames (lastName,firstName,col4) values
('Smith','John',1),('Smithers','JohnSomeone',1),('Smith3','John4324',1),('Smi','Jonathan',1),('Smith123x$FA','Joh',1),('Smi3jfif','jkdid',1),('r3','fe2',1);
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
insert myNames (lastName,firstName,col4) select lastname,firstname,col4 from mynames;
select count(*) from myNames;
-- 458k rows
select count(*)
from myNames
where lastname like 'smi%';
-- 393216 rows
select count(*)
from myNames
where lastname like 'smi%' and firstname like 'joh%';
-- 262144 rows
Explain
gengiver voodoo-tal for rows
. Voodoo? Ja, fordi en forespørgsel, der potentielt kører i en time, beder du explain
for at give dig et uklart tal, ikke køre det, og give dig det svar på 2 sekunder eller mindre. Betragt ikke disse for at være reelle antal #'er for kriterier, når det køres for rigtigt, uden explain
.
explain
select count(*)
from myNames
where lastname like 'smi%';
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
| 1 | SIMPLE | myNames | range | lastname | lastname | 302 | NULL | 233627 | Using where; Using index |
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
explain
select count(*)
from myNames
where lastname like 'smi%' and firstname like 'joh%' and col4=1;
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
| 1 | SIMPLE | myNames | range | lastname | lastname | 604 | NULL | 233627 | Using where; Using index |
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
-- the below chunk is interest. Look at the Extra column
explain
select count(*)
from myNames
where lastname like 'smi%' and firstname like 'joh%' and col4=1;
+----+-------------+---------+------+---------------+------+---------+------+--------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+---------+------+---------------+------+---------+------+--------+-------------+
| 1 | SIMPLE | myNames | ALL | lastname | NULL | NULL | NULL | 457932 | Using where |
+----+-------------+---------+------+---------------+------+---------+------+--------+-------------+
explain
select count(*)
from myNames
where firstname like 'joh%';
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
| 1 | SIMPLE | myNames | index | NULL | lastname | 604 | NULL | 453601 | Using where; Using index |
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
analyze table myNames;
+----------------------+---------+----------+----------+
| Table | Op | Msg_type | Msg_text |
+----------------------+---------+----------+----------+
| so_gibberish.mynames | analyze | status | OK |
+----------------------+---------+----------+----------+
select count(*)
from myNames where left(lastname,3)='smi';
-- 393216 -- the REAL #
select count(*)
from myNames where left(lastname,3)='smi' and left(firstname,3)='joh';
-- 262144 -- the REAL #
explain
select lastname,firstname
from myNames
where lastname like 'smi%' and firstname like 'joh%';
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+
| 1 | SIMPLE | myNames | range | lastname | lastname | 604 | NULL | 226800 | Using where; Using index |
+----+-------------+---------+-------+---------------+----------+---------+------+--------+--------------------------+