By optimizing sql index

Optimized sql statement the most important thing is to rational use of the index, here are some principles about the use of the index:

1. The most left-prefix matching principle.
mysql will always be matched to the right until it encounters a range queries (>, <, between, like ) to stop the match. So try to "=" in front of the condition, the range queries (>, <, between, like ) in the final condition.
Example:
do not use the index b:
WHERE. 1 and A = C> 0 and b = 2

B index will be used:
WHERE. 1 and A = 2 and b = C> 0


2 to select a high-sensitive column as an index.
Discrimination formula is count (distinct col) / count ( *), the proportion of repeat field is not represented, the greater the ratio the smaller the number of records in our scan.

3. When data is taken over a full 20% of the data table, do not use the index.

4. Note that some of the rules using the Win like
Example:
do not use indexes:
like '%% L'
like '% L'

Use Index:
like '% L'


5. Try to convert or union all
cases:
without using an index:
SELECT * WHERE from User name = 'A' or Age = '20 '

使用索引:
select * from user where name='a' union all select * from user where age='20'


6. fields plus function does not use the index. Therefore, as far as possible on the function values.
Example:
do not use indexes:
WHERE TRUNCATE (. Price). 1 =

Use Index:
WHERE. Price>. Price. 1 and <2


7. If digital as characters, numbers requires quotes, or mysql automatically applied on the column data type conversion functions.
Example:
indexes are not used
where mobile = 18534874321

Using an index
where mobile = '18534874321'


8. The field operator does not use the index added. So far as possible the operation on numerical
Example:
do not use indexes:
the SELECT ACCOUNT_NAME, the WHERE TRANSACTION AMOUNT + AMOUNT the FROM 3000> 5000;

使用索引:
SELECT ACCOUNT_NAME, AMOUNT FROM TRANSACTION WHERE AMOUNT > 2000 ;


9. When the combination index, the first column must be included.
Example:
ALTER Table Test the Add index (A, B, C):

Without using an index:
WHERE = B. 1, C = 2
WHERE. 1 B =
WHERE C = 2

Use Index:
WHERE A =. 1, B =. 1, C = 2
WHERE A =. 1, B =. 1
WHERE. 1 = A, 2 = C


10 is null or avoid using NU Not IS LL
Example:
do not use indexes:
the SELECT ... the FROM the DEPARTMENT the WHERE DEPT_CODE the IS the NOT NULL;

Use the index:
the SELECT ... the FROM the DEPARTMENT the WHERE DEPT_CODE> 0;


Does not use an index equal to 11. (! =)
Without using an index:
the SELECT ACCOUNT_NAME the WHERE the FROM TRANSACTION AMOUNT = 0;!

使用索引:
SELECT ACCOUNT_NAME FROM TRANSACTION WHERE AMOUNT >0;


12.ORDER BY clause is used only in the index under the following conditions:
the ORDER BY columns must all contain the same arrangement order in the index and maintained in the index.
The ORDER BY can not have both ASC DESC
example:
ALTER Table the Add index T1 (A, B);
ALTER index the Add Table T1 (C);

Without using an index:
SELECT * from T1 by Order A, C; index is not a
select * from t1 order by b; a combination of a first index column does not appear
select * from t1 order by a asc , b desc; mixing ASC and DESC

select * from t1 where a = 1 order by c; where the index is not the same, and the order by using, where the use of the index, order by not used.
Using an index:
SELECT * from T1 Order by A, B;
SELECT * from T1 Order WHERE A =. 1 Order by B;
SELECT * from T1 Order WHERE A =. 1 Order by A, B;
SELECT * from T1 Order by A desc, desc B;
SELECT * from T1 WHERE Order. 1 by C = C;


13. The index is not better. mysql need resources to maintain the index, any data changes (additions and deletions) would jointly modify the value of the index. Therefore, the need to bring balance to consider index additions and deletions to the query acceleration and deceleration.
Other Notes:
1. Avoid the use of * SELECT
2. Table possible connection (join) in place of the sub-query from T1 WHERE A * SELECT in (B SELECT from T2)
3. Performance Table connector> (not) exists> ( Not) in
. 1) substituting exists in
inefficient:
the SELECT *
the FROM the EMP
the WHERE the EMPNO> 0
the AND the DEPTNO the iN (the SELECT the DEPTNO
the FROM the DEPT
the WHERE the LOC = 'MELB')

高效:
SELECT *
FROM EMP
WHERE EMPNO > 0
AND EXISTS (SELECT ‘X’
FROM DEPT
WHERE DEPT.DEPTNO = EMP.DEPTNO
AND LOC = ‘MELB’)

2)用not exists代替not in
低效:
SELECT …
FROM EMP
WHERE DEPT_NO NOT IN (SELECT DEPT_NO
FROM DEPT
WHERE DEPT_CAT=’A’);

高效:
SELECT ….
FROM EMP E
WHERE NOT EXISTS (SELECT ‘X’
FROM DEPT D
WHERE D.DEPT_NO = E.DEPT_NO
AND DEPT_CAT = ‘A’);

3)用表连接代替exists
exits:
SELECT ENAME
FROM EMP E
WHERE EXISTS (SELECT ‘X’
FROM DEPT
WHERE DEPT_NO = E.DEPT_NO
AND DEPT_CAT = ‘A’);

表连接:
SELECT ENAME
FROM DEPT D,EMP E
WHERE E.DEPT_NO = D.DEPT_NO
AND DEPT_CAT = ‘A’ ;


14. A sorting remove unnecessary
inefficient:
SELECT COUNT (*) from (SELECT * WHERE User ID from> 40 by Order ID);

高效:
select count(*) from (select * from user where id > 40);


15.having -> where
avoid using HAVING clause, HAVING fishes filtered result set will only retrieve all records after this process requires sorting, if the total number of other operations can limit the records of the WHERE clause, then. can reduce this overhead.
inefficient:
the SELECT * from the User Group by the above mentioned id the HAVING the above mentioned id> 40;

高效:
select * from user where id > 40 group by id;


16. Unless really need to remove duplicate rows, or else try to use union all instead of union. Because the union will bring their own distinct operations, at great cost.

Use explain to view sql performance
1.explain Usage: Before you can select plus explain.
For example:
EXPLAIN the SELECT * from the Test;

Note: explain and does not actually run the statement, but only returns the execution plan.
How to see the execution plan? A simple optimization principle: Let sql read as few rows.

2.实战案例1:
问题语句运行超过5s:
SELECT `branch`.`id`, `branch`.`name`, `branch`.`registered_time`, `branch_region`.`region_id`, `user`.`username`, `user`.`mobile`, count(o.order_id) as order_num
FROM (`branch`)
LEFT JOIN `user` ON `user`.`branch_id` = `branch`.`id`
LEFT JOIN `branch_role` ON `branch_role`.`id` = `user`.`role_id`
LEFT JOIN `branch_region` ON `branch_region`.`branch_id` = `branch_role`.`branch_id`
LEFT JOIN `orders` o ON `branch`.`id` = `o`.`supplier_id`
WHERE branch.id NOT IN (select supplier_id from signing where seller_id=6683 and status < 6)
AND `branch`.`group` = 'SUPPLIER'
AND `branch_role`.`flag` = 'ADMINISTRATOR'
AND `branch`.`status` = 'NORMAL'
GROUP BY `branch`.`id`
ORDER BY `branch`.`registered_time` desc
LIMIT 20;

Use explain to view the execution plan:

According to the principle of "as little as possible to read data" and found that the largest number of rows read step of reading the 4792 line. And then found that this step did not use the index (NULL). And this is not the index of the table is supplier_id orders of columns.
Try indexed:
ALTER index the Add Orders Table (supplier_id);

Use explain again to view an execution plan:

This step can be seen that the use of the index and reduce the number of rows read to the 599 line.
The actual implementation of what, seconds out.

Meaning 3.explain implementation plan of the fields:
1) the above mentioned id: execution order of the statements, reverse execution
2) select_type: mainly in the following types:
lsimple: represents a simple select, there is no union and sub-query
lprimary: the outermost select . In the statement has a sub query, select query is the outermost Primary
lunion: The second sentence of Union or is the man behind a
lunion result: union results
lsubquery: subquery first select

Guess you like

Origin www.cnblogs.com/ericz2j/p/11109203.html