Use OR to perform SQL adjustment

xiaoxiao2021-03-06  104

problem:

How should such SQL optimize?

SELECT * from Sys_User

Where user_code = 'zhangyong'

OR user_code in

(SELECT GRP_CODE

From Sys_GRP

Where sys_grp.user_code = 'zhangyong')

Execution Plan

-------------------------------------------------- ------------

0 SELECT Statement Optimizer = Rule

1 0 Filter

2 1 Table Access (Full) of 'Sys_User'

3 1 Index (Unique Scan) of 'PK_SYS_GRP' (UNIQUE)

Statistics

-------------------------------------------------- ------------

14 Recursive Calls

4 DB Block Gets

30590 CONSISTENT GETS

0 Physical READS

0 redo size

1723 BYTES SENT VIA SQL * NET to Client

425 Bytes Received Via SQL * Net from Client

2 SQL * NET ROUNDTRIPS TO / FROM Client

0 Sorts (Memory)

0 Sorts (Disk)

3 Rows Processed

The number of records returned in the inside is generally only one or two, but the data of the sys_user table is much data, how can this SQL drive table with SYS_GRP? The records in the table are as follows:

SQL> SELECT Count (*) from sys_grp;

Count (*) ---------- 25130

SQL> SELECT Count (*) from sys_user;

Count (*)

------------

15190

optimization:

Reduce logical reading is one of the basic principles of optimizing SQL

We tried to speed up the execution of SQL by reducing logical reading.

Here we use the OR to expand to overwrite the SQL query:

Select * from sys_user where user_code = 'zhangyong'

Union all

Select * from sys_user where user_code <> zhangyong '

And user_code in (SELECT GRP_CODE AUS_GRP where sys_grp.user_code = 'zhangyong')

Statistics

-------------------------------------------------- ------------

0 Recursive Calls

0 DB Block Get

130 Consistent Gets

0 Physical READS

0 redo size

1723 BYTES SENT VIA SQL * NET to Client

425 Bytes Received Via SQL * Net from Client

2 SQL * NET ROUNDTRIPS TO / FROM Client

1 Sorts (Memory)

0 Sorts (Disk)

3 Rows Processed

Execution Plan

-------------------------------------------------- ------------

0 Select Statement Optimizer = Rule1 0 Union-all

2 1 Table Access (by index rowid) of 'sys_user'

3 2 INDEX (Unique Scan) of 'Pk_sys_User' (Unique)

4 1 Nested Loops

5 4 View of 'VW_NSO_1'

6 5 sort (unique)

7 6 Table Access (by index rowid) of 'sys_grp'

8 7 Index (Range Scan) of 'FK_SYS_USER_CODE' (Non-Unique)

9 4 Table Access (By Index Rowid) of 'Sys_USER'

109 Index (Unique Scan) of 'PK_SYS_USER' (UNIQUE)

We noticed that by rewriting, logical reading is reduced to 130, from 30590 to 130 this is a huge improvement, reducing logic reads will eventually reduce resource consumption, improve SQL execution efficiency.

This rewrite converts Filter to Nest Loop, and the index is fully utilized. Thus greatly improving performance.

We also noticed that a sort is introduced here.

Sort from this step:

-------------------------------------------------- ---------------------------------------

6 5 sort (unique)

7 6 Table Access (by index rowid) of 'sys_grp'

8 7 Index (Range Scan) of 'FK_SYS_USER_CODE' (Non-Unique)

-------------------------------------------------- ----------------------------------------

In the 'sys_grp' table, user_code is the unique key value in the IN value, to do sort unique sort, remove the repetition value

The UNION ALL here is no need to sort

转载请注明原文地址:https://www.9cbs.com/read-101012.html

New Post(0)