Əsas səhifə > MySQL 5.6, Performance tests and tips > MySQL 5.6.10 Query optimizer (performance test)

MySQL 5.6.10 Query optimizer (performance test)

Təbii ki 5.6.10 versiya ilə bir çox yeniliklər gəlib.
Və əsas səs gətirən hadisələrdən biri Query Optimizer-in inkişafıdır. Çox dərinliyə getmədən nə qədər əlavələrin olduğuna siz də baxa bilərsiniz:

5.5.30 versiya üçün:

mysql [localhost] {msandbox} (employees) > select @@optimizer_switch\G
*************************** 1. row ***************************
@@optimizer_switch:
index_merge=on,
index_merge_union=on,
index_merge_sort_union=on,
index_merge_intersection=on,
engine_condition_pushdown=on
1 row in set (0.00 sec)

5.6.10 versiya üçün:

mysql> select @@optimizer_switch\G
*************************** 1. row ***************************
@@optimizer_switch: 
index_merge=on,
index_merge_union=on,
index_merge_sort_union=on,
index_merge_intersection=on,
engine_condition_pushdown=on,
index_condition_pushdown=on,
mrr=on,
mrr_cost_based=on,
block_nested_loop=on,
batched_key_access=off,
materialization=on,
semijoin=on,
loosescan=on,
firstmatch=on,
subquery_materialization_cost_based=on,
use_index_extensions=on
1 row in set (0.00 sec)

Bəli MySQL optimizer indi daha ağıllıdır necə deyərlər. Və test üçün biz employees database-ini götürəcik. Bu database-i siz də yükləyə bilərsiniz:
employees_db

Və bu database-dəki employees cədvəli. Cədvəldə 300.024 record var.Cədvəl strukturu aşağıdakı kimidir:

mysql> desc employees;
+------------+---------------+------+-----+---------+-------+
| Field      | Type          | Null | Key | Default | Extra |
+------------+---------------+------+-----+---------+-------+
| emp_no     | int(11)       | NO   | PRI | NULL    |       |
| birth_date | date          | NO   |     | NULL    |       |
| first_name | varchar(14)   | NO   |     | NULL    |       |
| last_name  | varchar(16)   | NO   |     | NULL    |       |
| gender     | enum('M','F') | NO   |     | NULL    |       |
| hire_date  | date          | NO   |     | NULL    |       |
+------------+---------------+------+-----+---------+-------+
6 rows in set (0.00 sec)

Dolayısı ilə 1 dənə index var o da primary key.

Test 1:

select emp_no from employees where first_name='Marco'

MySQL 5.6.10:

MySQL 5.5.30:

və yuxarıdakı QEP-dən də aydın olduğu kimi MySQL 5.6.10 test edilmiş query-nin nəticəsini bizə hazırlayıb verməsi üçün 299,645 row-nu oxumalıdır. 5.5.30 isə 300,856.
Lakin query response time-da elə də fərq yoxdur hər 2-si 0.10 sec çəkdi.

Test 2:
Sözsüz ki, məntiqlə düşündükdə belə nəticəyə gəlmək olar ki, əgər biz first_name-lə axtarış ediriksə onu index-ləməliyik:

alter table employees add index(first_name);
select emp_no from employees where first_name='Marco'

MySQL 5.6.10:

MySQL 5.5.30:

QEP-lər tamamilə eynidir. Gördüyümüz kimi emp_no və first_name hər ikisi index-ləndiyi üçün MySQL məlumatı birbaşa index-dən oxuyur.
Bu həmçinin aşağıdakı query-lər üçün də keçərlidir:

select emp_no from employees where first_name like '%mar%';
select emp_no from employees where first_name like 'Mar%';

Təbii ki scan olunacaq row sayı artacaq çünki ehtimallar çoxalır lakin istənilən halda index-dən istifadə olunacaq.

Test 3:
İndi isə query-mizə 1 dənə index-lənməmiş column əlavə edək:

select emp_no,last_name from employees where first_name='Marco';

indiki halda bu index-siz column last_name-dir.
Yazının da yazılma səbəbi məhz şəxsən müəyyən etdiyim MySQL 5.6.10-nun bu gözəl xüsusiyyətdir. Aşağıya diqqət😉

MySQL 5.6.10:

-- 1
select last_name,emp_no from employees where first_name='Marco';

-- 2
select emp_no,last_name from employees where first_name like 'Marc%';

-- 3
select emp_no,last_name from employees where first_name like 'Mar%';

-- 4
select emp_no,last_name from employees where first_name like 'Ma%';

-- 5
select emp_no,last_name from employees where first_name like 'M%';

Şəkillərdəki EXTRA və rows -lara fikir versəniz görərsiniz ki, MySQL 5.6.10 5 variantın 4-ündə İndex Condition-dan istifadə etdi. Yalnız sonuncu like ‘M%’-dən başqa. Bunun da səbəbi çox aşkardı. M% böyük ehtimal verir bu zaman MySQL Optimizer M-lə başlayan-ları index vasitəsilə yoxlamaq əvəzinə sadəcə full scan etməyi üstün tutur. Optimizer bunun daha faydalı olacağına qənaət gətirib elə biz də həmçinin🙂

İndi isə eyni testləri MySQL 5.5.30 üçün edək.
MySQL 5.5.30:

-- 1
select last_name,emp_no from employees where first_name='Marco';

-- 2
select emp_no,last_name from employees where first_name like 'Marc%';

-- 3
select emp_no,last_name from employees where first_name like 'Mar%';

-- 4
select emp_no,last_name from employees where first_name like 'Ma%';

-- 5
select emp_no,last_name from employees where first_name like 'M%';

Gördüyünüz kimi istənilən halda Using İndex Condition istifadə olunmadı. Səbəb? Çünki bu xüsusiyyət yalnız MySQL 5.6.10-da var. Ümumiyyətlə bu versiya çox səs gətirəcək deyə bilərik. Həmçinin siz MariaDB 10.0-a da baxa bilərsiniz. Bu MySQL 5.6.10 ilə eynidir.

Bəs nədir bu Using İndex Condition? Daha ətraflı: index-condition-pushdown-optimization
Qısa olaraq: ICP can reduce the number of times the storage engine must access the base table and the number of times the MySQL server must access the storage engine.

Onu da qeyd etməkdə fayda var ki, siz də öz localhost/server-inizdə 2 ve daha artıq MySQL versiyanı qurub test edə bilərsiniz. Bunun üçün xüsusi tool MySQL Sandbox-dan istifadə edə bilərsiniz. Bu haqda artıq məqalə yazmışam:
Sandbox on Centos

Təşəkkürlər😉

  1. Hələlik heç bir şərh yoxdur
  1. No trackbacks yet.

Bir cavab yazın

Sistemə daxil olmaq üçün məlumatlarınızı daxil edin və ya ikonlardan birinə tıklayın:

WordPress.com Loqosu

WordPress.com hesabınızdan istifadə edərək şərh edirsinz. Çıxış / Dəyişdir )

Twitter rəsmi

Twitter hesabınızdan istifadə edərək şərh edirsinz. Çıxış / Dəyişdir )

Facebook fotosu

Facebook hesabınızdan istifadə edərək şərh edirsinz. Çıxış / Dəyişdir )

Google+ foto

Google+ hesabınızdan istifadə edərək şərh edirsinz. Çıxış / Dəyişdir )

%s qoşulma

%d bloqqer bunu bəyənir: