[20120410]9i下索引與空值查詢以及非空約束.txt
[20120410]9i下索引與空值查詢以及非空約束.txt
前幾天在最佳化9i的一條sql語句時,發現一個奇怪的現象,查詢條件是is null,發現竟然可以使用索引,感覺很奇怪,再仔細看原來
查詢欄位存在一個非空約束,對比了10g以及11g的版本,感覺10g與11g改進不少。
測試如下:
1.建立測試環境:
3.如果加入非空約束,情況會如何呢?
--發現加入非空約束後,可以使用索引。
4.在11g下測試,10g測試留給大家:
--可以發現走的是全表掃描,但是過濾條件是NULL IS NOT NULL,肯定為false。結果根本不讀表,所以邏輯讀為0.
前幾天在最佳化9i的一條sql語句時,發現一個奇怪的現象,查詢條件是is null,發現竟然可以使用索引,感覺很奇怪,再仔細看原來
查詢欄位存在一個非空約束,對比了10g以及11g的版本,感覺10g與11g改進不少。
測試如下:
1.建立測試環境:
SQL> select * from v$version;
BANNER
----------------------------------------------------------------
Oracle9i Enterprise Edition Release 9.2.0.8.0 - Production
PL/SQL Release 9.2.0.8.0 - Production
CORE 9.2.0.8.0 Production
TNS for 32-bit Windows: Version 9.2.0.8.0 - Production
NLSRTL Version 9.2.0.8.0 - Production
SQL> create table t tablespace users as select rownum id,'test' name from dual connect by level <=1000;
Table created.
SQL> desc t;
Name Null? Type
------ -------- --------
ID NUMBER
NAME CHAR(4)
--可以發現ID欄位可以為空。
SQL> create index i_t_id on t(id) tablespace users;
Index created.
SQL> exec dbms_stats.gather_table_stats(user,'T');
PL/SQL procedure successfully completed.
2.測試:
SQL> set autot traceonly ;
SQL> select * from t where id is null ;
no rows selected
Execution Plan
----------------------------------------------------------
0 SELECT STATEMENT ptimizer=CHOOSE (Cost=2 Card=1 Bytes=8)
1 0 TABLE ACCESS (FULL) OF 'T' (Cost=2 Card=1 Bytes=8)
Statistics
----------------------------------------------------------
0 recursive calls
0 db block gets
4 consistent gets
0 physical reads
0 redo size
297 bytes sent via SQL*Net to client
376 bytes received via SQL*Net from client
1 SQL*Net roundtrips to/from client
0 sorts (memory)
0 sorts (disk)
0 rows processed--可以發現執行計劃走的是全表掃描。
3.如果加入非空約束,情況會如何呢?
SQL> alter table t modify id not null ;
Table altered.
SQL> set autot traceonly ;
SQL> select * from t where id is null ;
no rows selected
Execution Plan
----------------------------------------------------------
0 SELECT STATEMENT ptimizer=CHOOSE (Cost=1 Card=1 Bytes=8)
1 0 TABLE ACCESS (BY INDEX ROWID) OF 'T' (Cost=1 Card=1 Bytes=8)
2 1 INDEX (RANGE SCAN) OF 'I_T_ID' (NON-UNIQUE) (Cost=1 Card=1)
Statistics
----------------------------------------------------------
0 recursive calls
0 db block gets
2 consistent gets
0 physical reads
0 redo size
297 bytes sent via SQL*Net to client
376 bytes received via SQL*Net from client
1 SQL*Net roundtrips to/from client
0 sorts (memory)
0 sorts (disk)
0 rows processed
--發現加入非空約束後,可以使用索引。
4.在11g下測試,10g測試留給大家:
SQL> select * from v$version ;
BANNER
--------------------------------------------------------------------------------
Oracle Database 11g Enterprise Edition Release 11.2.0.1.0 - 64bit Production
PL/SQL Release 11.2.0.1.0 - Production
CORE 11.2.0.1.0 Production
TNS for Linux: Version 11.2.0.1.0 - Production
NLSRTL Version 11.2.0.1.0 - Production
SQL> create table t as select rownum id,'test' name from dual connect by level<=1000;
Table created.
SQL> create index i_t_id on t(id);
Index created.
SQL> exec dbms_stats.gather_table_stats(user,'T');
PL/SQL procedure successfully completed.
SQL> select * from t where id is null ;
no rows selected
SQL> @dpc
PLAN_TABLE_OUTPUT
--------------------------------------------------------
SQL_ID 9gsqcvc0dxtd4, child number 0
-------------------------------------
select * from t where id is null
Plan hash value: 1601196873
--------------------------------------------------------
| Id | Operation | Name | E-Rows | Cost (%CPU)|
--------------------------------------------------------
| 0 | SELECT STATEMENT | | | 3 (100)|
|* 1 | TABLE ACCESS FULL| T | 1 | 3 (0)|
--------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
1 - filter("ID" IS NULL)
Note
-----
- Warning: basic plan statistics not available. These are only collected when:
* hint 'gather_plan_statistics' is used for the statement or
* parameter 'statistics_level' is set to 'ALL', at session or system level
24 rows selected.
SQL> alter table t modify id not null;
Table altered.
SQL> set autot traceonly
SQL> select * from t where id is null ;
no rows selected
Execution Plan
----------------------------------------------------------
Plan hash value: 1322348184
---------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
---------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 9 | 0 (0)| |
|* 1 | FILTER | | | | | |
| 2 | TABLE ACCESS FULL| T | 1000 | 9000 | 3 (0)| 00:00:01 |
---------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
1 - filter(NULL IS NOT NULL)
Statistics
----------------------------------------------------------
0 recursive calls
0 db block gets
0 consistent gets
0 physical reads
0 redo size
396 bytes sent via SQL*Net to client
508 bytes received via SQL*Net from client
1 SQL*Net roundtrips to/from client
0 sorts (memory)
0 sorts (disk)
0 rows processed
--可以發現走的是全表掃描,但是過濾條件是NULL IS NOT NULL,肯定為false。結果根本不讀表,所以邏輯讀為0.
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/267265/viewspace-720779/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- 資料遷移判斷非空約束
- Sql Server 自定義約束 實現:某列 可空,但非空值唯一不重複SQLServer
- 使用組合索引處理包含空值的查詢索引
- [20170516]nvl與非NULL約束.txtNull
- mybatis配置:map查詢空值返回MyBatis
- sql: 查詢約束SQL
- 查詢oracle表的資訊(表,欄位,約束,索引)Oracle索引
- [20170516]nvl與非NULL約束2.txtNull
- Kotlin可空型別與非空型別以及`lateinit` 的作用Kotlin型別
- 肯定賦值斷言與非空斷言賦值
- [20201201]約束大寫與查詢.txt
- 需要取最近的非空值
- Oracle 查詢表大小以及表空間使用率Oracle
- 約束:確保資料的完整性(主鍵,唯一,檢查,預設,非空,外來鍵)
- Android WorkManager工作約束,延遲與查詢工作Android
- oracle表空間查詢Oracle
- mysql 查詢undo空間MySql
- 表空間大小查詢
- 表空間查詢資訊
- 空間修改及查詢
- 【CONSTRAINT】具有唯一性約束的列是否可以插入空值AI
- 主鍵(PK)與非空唯一索引(Unique Index)的區別索引Index
- Oracle下查詢臨時表空間佔用率Oracle
- 查詢表空間已使用空間和空閒空間的簡單檢視
- oracle查詢表空間的空間佔用情況Oracle
- 表空間查詢和管理
- 表空間相關查詢
- 阿里Java學習路線:階段 2:資料庫開發-SQL進階及查詢練習:課時6:非空和唯一約束阿里Java資料庫SQL
- 臨時表空間的空間使用情況查詢
- 查詢(看)表的主鍵、外來鍵、唯一性約束和索引索引
- 表空間使用量查詢
- SQLAlchemy in 查詢空列表問題分析SQL
- 查詢表空間使用情況
- Mybatis模糊查詢結果為空MyBatis
- 關於oracle的空間查詢Oracle
- Oracle空間查詢 ORA-28595Oracle
- 藉助索引+非空優化distinct操作一例索引優化
- Oracle 9i 約束條件(轉)Oracle