oracle 優化器模式 optimizer_mode

os: centos 7.4
db: oracle 11.2.0.4

版本

# cat /etc/centos-release
CentOS Linux release 7.4.1708 (Core) 
# 
# su - oracle
Last login: Tue Jan 21 03:40:05 CST 2020 on pts/0
$ sqlplus / as sysdba;

SQL*Plus: Release 11.2.0.4.0 Production on Mon Feb 3 10:29:09 2020

Copyright (c) 1982, 2013, Oracle.  All rights reserved.


Connected to:
Oracle Database 11g Enterprise Edition Release 11.2.0.4.0 - 64bit Production
With the Partitioning, Real Application Clusters, Automatic Storage Management, OLAP,
Data Mining and Real Application Testing options

SQL> set lines 300;
SQL> set pages 300;
SQL> 
SQL> select * from v$version;

BANNER
--------------------------------------------------------------------------------
Oracle Database 11g Enterprise Edition Release 11.2.0.4.0 - 64bit Production
PL/SQL Release 11.2.0.4.0 - Production
CORE	11.2.0.4.0	Production
TNS for Linux: Version 11.2.0.4.0 - Production
NLSRTL Version 11.2.0.4.0 - Production

SQL> 

optimizer_mode

默認值爲 all_rows

SQL> show parameter optimizer_mode;

NAME				     TYPE	 VALUE
------------------------------------ ----------- ------------------------------
optimizer_mode			     string	 ALL_ROWS
SQL> 

optimizer_mode 有幾種枚舉值呢?

在這裏插入圖片描述
first_rows_n

The optimizer uses a cost-based approach and optimizes with a goal of best response time to return the first n rows (where n = 1, 10, 100, 1000).

first_rows

The optimizer uses a mix of costs and heuristics to find a best plan for fast delivery of the first few rows.

all_rows

The optimizer uses a cost-based approach for all SQL statements in the session and optimizes with a goal of best throughput (minimum resource use to complete the entire statement).

在 session 級別修改試試看

SQL> alter session set optimizer_mode=first_rows;

SQL> alter session set optimizer_mode=first_rows_1;

SQL> alter session set optimizer_mode=first_rows_10;

SQL> alter session set optimizer_mode=first_rows_100;

SQL> alter session set optimizer_mode=first_rows_1000;

以上都設置成功,如果那個 n 爲別的數字了?可以看到報錯了

SQL> alter session set optimizer_mode=first_rows_2;
ERROR:
ORA-00096: invalid value FIRST_ROWS_2 for parameter optimizer_mode, must be
from among first_rows_1000, first_rows_100, first_rows_10, first_rows_1,
first_rows, all_rows, choose, rule

SQL> alter session set optimizer_mode=first_rows_9;
ERROR:
ORA-00096: invalid value FIRST_ROWS_9 for parameter optimizer_mode, must be
from among first_rows_1000, first_rows_100, first_rows_10, first_rows_1,
first_rows, all_rows, choose, rule

SQL> alter session set optimizer_mode=first_rows_10000;
ERROR:
ORA-00096: invalid value FIRST_ROWS_10000 for parameter optimizer_mode, must be
from among first_rows_1000, first_rows_100, first_rows_10, first_rows_1,
first_rows, all_rows, choose, rule

另外有個 first_rows(n) 的hint,這個 n 是可以爲其餘數字的,如下:

SQL> set lines 300;
set pages 300;

SQL> 
SQL> show parameter optimizer_mode;

NAME				     TYPE	 VALUE
------------------------------------ ----------- ------------------------------
optimizer_mode			     string	 ALL_ROWS


SQL> set autotrace traceonly;
SQL> 
SQL> select/*+ FIRST_ROWS(20)*/ *
  from tmp_t0 a
 where 1=1
   and a.c1='123'
;   

no rows selected


Execution Plan
----------------------------------------------------------
Plan hash value: 1080252402

---------------------------------------------------------------------------------------------
| Id  | Operation		    | Name	    | Rows  | Bytes | Cost (%CPU)| Time     |
---------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT	    |		    |	  1 |	165 |	  1   (0)| 00:00:01 |
|   1 |  TABLE ACCESS BY INDEX ROWID| TMP_T0	    |	  1 |	165 |	  1   (0)| 00:00:01 |
|*  2 |   INDEX RANGE SCAN	    | IDX_TMP_T0_X1 |	  1 |	    |	  1   (0)| 00:00:01 |
---------------------------------------------------------------------------------------------

Predicate Information (identified by operation id):
---------------------------------------------------

   2 - access("A"."C0"='123')


Statistics
----------------------------------------------------------
	  0  recursive calls
	  0  db block gets
	  1  consistent gets
	  0  physical reads
	  0  redo size
	522  bytes sent via SQL*Net to client
	509  bytes received via SQL*Net from client
	  1  SQL*Net roundtrips to/from client
	  0  sorts (memory)
	  0  sorts (disk)
	  0  rows processed


參考:
https://docs.oracle.com/cd/E11882_01/server.112/e40402/initparams171.htm#REFRN10145
https://docs.oracle.com/cd/E11882_01/server.112/e41573/optimops.htm#i38217

發佈了732 篇原創文章 · 獲贊 70 · 訪問量 51萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章