【TUNE_ORACLE】Oracle Hint之常用Hint功能概述(一)

Attack_on_Jager發表於2021-02-11

說明 

1.整理了一些本人平時SQL 調優中常用到的一些Hint,方便大家參考

2.Hint相關文章地址:

Oracle Hint之概念與用法: http://blog.itpub.net/69992972/viewspace-2756965/

Oracle Hint之常用Hint功能概述(一): http://blog.itpub.net/69992972/viewspace-2757087/

Oracle Hint之常用Hint功能概述(二): http://blog.itpub.net/69992972/viewspace-2757182/

Oracle Hint之常用Hint功能概述(三): http://blog.itpub.net/69992972/viewspace-2757238/

Oracle Hint之常用Hint功能概述(四): http://blog.itpub.net/69992972/viewspace-2757242/

Oracle Hint之常用Hint功能概述(五): http://blog.itpub.net/69992972/viewspace-2757273/


索引Hint

Hint

功能概述

舉例

/*+ index(tab idx_name)   */

使最佳化器對指定的表使用索引掃描。可用於函式、域(domain)、 B-tree, bitmap 和 bitmap join索引等

SELECT /*+ INDEX     (employees department_idx)*/ employee_id, department_id FROM emp WHERE   department_id > 20;

/*+ no_index(tab   idx_name) */

強制最佳化器不使用指定的索引掃描


/*+ index_join(tab   idx_name) */

讓最佳化器使用指定的索引作為訪問路徑進行索引關聯。不同之處是select語句中查詢列必須包含在索引中,可避免回表。因為當謂詞中的列都有索引時,可直接透過索引關聯,而這個hint可以將同一張表的不同索引進行合併,最佳化器只需掃描這些索引即可,不需要回表

SELECT /*+     INDEX_JOIN(t manager_idx department_idx) */ department_id FROM emp t   WHERE manager_id < 100 AND department_id < 20;

/*+ index_ffs(tab   idx_name) */

強制最佳化器對指定索引使用Fast Full Scan方式掃描。但是必須select語句中查詢列必須包含在索引中,可避免回表


/*+ index_ss(tab   idx_name) */

強制最佳化器對指定索引使用Skip   Scan方式掃描


/*+ index_asc(tab   idx_name) */

使最佳化器對指定的表使用索引掃描。一般來說該hint不會更改索引的預設順序,但如果該語句使用索引範圍(index range scan)掃描,則Oracle資料庫將按其索引值的升序掃描索引條目


/*+ index_desc(tab   idx_name) */

使最佳化器對指定的表使用降序索引掃描。如果該語句使用索引範圍掃描並且索引在升序,則按索引值的降序掃描索引條目。在分割槽索引中,結果在每個分割槽中按降序排列。對於降序索引,該hint有效地抵消了降序,從而以升序掃描了索引條目


/*+ index_combine(tab   idx_name) */

該hint可以使用任何型別的索引:bitmap,B-tree,或domain。如果未指定索引名,那麼最佳化器將隱式地將INDEX hint應用於所有索引,並使用盡可能多的索引。如果指定索引名,則最佳化器將使用所有合法且有效的在hint中提到的索引,而不考慮成本

SELECT /*+ INDEX_COMBINE(t manager_idx   department_idx)   */ * FROM emp t WHERE manager_id = 10 OR department_id   = 20;



表連線Hint
 

Hint

功能概述

舉例

/*+ ordered */

該hint讓最佳化器按照表在FROM子句中出現的順序聯接表。Oracle官方建議使用LEADING hint,該提示比ORDERED提示更通用。當從需要聯接的SQL語句中省略ORDERED提示時,最佳化程式將選擇聯接表的順序。如果使用者知道最佳化器不瞭解有關從每個表中選擇的行數的資訊,則可能需要使用ORDERED hint來指定連線順序。這樣可以讓使用者比最佳化器更好地選擇內部和外部表

SELECT  /*+   ORDERED */   o.order_id, c.customer_id, i.unit_price * i.quantity FROM   customers c, items i,   orders o WHERE c.cust_last_name = 'Smith' AND   o.customer_id = c.customer_id AND o.order_id = i.order_id;

/*+ leading(tab1   tab2) */

該hint是一個多表hint,可以指定多個表或檢視。 LEADING指示最佳化器將指定的表集用作執行計劃中的字首。指定的第一個表用於啟動聯接

SELECT   /*+ LEADING(e j) */ * FROM   emp e, departments d, job_history j WHERE e.department_id = d.department_id   AND e.hire_date = j.start_date;

/*+ use_nl(tab1   tab2) */

USE_NL提示指示最佳化器將指定的表用作內部表(被驅動表),以巢狀迴圈聯接的方式將每個指定的表連線至另一個行源。建議在LEADING和ORDERED這兩個hint中來使用USE_NL和USE_MERGE hint。當強制將引用表作為聯接的內部表時,最佳化器將使用這些hint。 如果引用的表是外部表,則忽略該hint

SELECT /*+     USE_NL(i h) */ h.customer_id, i.unit_price * i.quantity FROM orders h,   items i WHERE l.order_id = h.order_id;

/*+ use_nl_with_index(tab   idx_name) */

該hint讓最佳化器使用指定的表作為內部表,使用巢狀迴圈連線(NL)將指定的表連線到另一個行源

SELECT /*+ USE_NL_WITH_INDEX(i     item_product_ix) */ * FROM orders h, items i WHERE i.order_id = h.order_id   AND i.order_id > 2400;

/*+   use_merge(tab1 tab2) */

該hint讓最佳化器使用排序合併聯接(SMJ)將每個指定的表作為被驅動表與另一個行源聯接

SELECT /*+     USE_MERGE(employees departments) */ * FROM employees, departments   WHERE employees.department_id = departments.department_id;

/*+ use_hash(tab1   tab2) */

該hint讓最佳化器使用雜湊聯接將每個指定的表與另一個行源聯接

SELECT /*+ USE_HASH(l h) */ * FROM orders   h, items i WHERE i.order_id = h.order_id AND i.order_id > 2400;

/*+   driving_site(tab) */

該hint讓最佳化器在與資料庫選擇的節點不同的節點上(其他節點生效)執行查詢。適用於CBO和RBO。如果使用的是帶DBLINK的分散式查詢最佳化,則此hint會大大節省網路傳輸的資料量,但不能用於分散式DML和DDL

SELECT /*+     DRIVING_SITE(departments) */ * FROM emp e, departments@testdb WHERE   e.department_id = departments.department_id;

/*+ use_concat */

該hint讓最佳化器使用UNION   ALL set運算子將查詢的WHERE子句中的組合OR條件轉換為複合查詢(union all)。 如果沒有此hint,則僅當在使用串聯的查詢的成本比沒有串聯的成本低時,才會發生此轉換。 該hint覆蓋了成本考慮因素

SELECT /*+ USE_CONCAT */ * FROM emp e   WHERE manager_id = 1 OR department_id = 20;

/*+ merge_aj */

針對有子查詢的SQL,讓最佳化器強制執行排序合併反連線


/*+ hash_aj */

針對有子查詢的SQL,讓最佳化器強制執行HASH反連線


/*+ nl_aj */

針對有子查詢的SQL,讓最佳化器強制執行巢狀迴圈反連線


/*+ merge_sj */

針對有子查詢的SQL,讓最佳化器強制執行排序合併半連線


/*+ hash_sj */

針對有子查詢的SQL,讓最佳化器強制執行HASH半連線


/*+ nl_sj */

針對有子查詢的SQL,讓最佳化器強制執行巢狀迴圈半連線


注:
1. 表中所說的“行源”就是表的關聯列(連線列)

2. 對於/*+ no_use_xxx */這種hint,就是/*+ use_xxx */的“反義詞”,比如/*+ no_use_merge */,這裡就不多贅述了


來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/69992972/viewspace-2757087/,如需轉載,請註明出處,否則將追究法律責任。

相關文章