oracle hint push_pred,hints的push_pred应用-Oracle
hints的push_pred應用
在項目中優化了一條SQL,當時從40多秒減少到了2秒,感覺很有成就感,現在反過頭來又看了一次,覺得仍然有優化的余地,SQL如下
Sql代碼
SELECT DISTINCT A.CURTITLE AS CTITLE,
A.DMODIFYDATE,
A.NDOCID AS NDOCID,
A.NPROCID AS NPROCID,
B.CPROCNAME AS CPROCNAME,
B.NDAYS AS TRUE_DAYS,
(SYSDATE – A.DMODIFYDATE) AS DAYSLEFT,
A.NDOCSORTID AS NDOCSORTID,
A.NPROCSTATUS AS NPROCSTATUS,
C.CNAME AS DOCSORTNAME,
NVL(D.NJJCD, 0) NJJCD,
D.CDOCFROM AS CDOCFROM,
D.CDOCPRIORITY AS CDOCPRIORITY,
D.CWENHAO,
A.NFWQBOPT,
D.DW
FROM WF_DOC_GW A,
WF_PROCNAME B,
WF_DOCSORT C,
(SELECT ? NVL(CFWZH, ”) AS CWENHAO,
NVL(CFWDW, ‘ ‘) AS DW,
NDOCID,
NJJCD,
NVL(CDOCFROM, ‘ ‘) AS CDOCFROM,
NVL(CDOCPRIORITY, 0) AS CDOCPRIORITY
FROM WF_DOC_GW_SHOUWEN SW
UNION ALL
SELECT NVL(CWENHAO, ‘ ‘) AS CWENHAO,
NVL(CFWDW, ”) AS DW,
NDOCID,
NJJCD,
NVL(CDOCFROM, ‘本單位發文’) AS CDOCFROM,
NVL(CDOCPRIORITY, 0) AS CDOCPRIORITY
FROM WF_DOC_GW_FAWEN FW) D
WHERE A.NPROCID = B.NPROCID AND
A.NDOCID = D.NDOCID AND
A.NDOCSORTID = C.NDOCSORTID AND
C.NDOCSORTID IN (1, 2) AND
(A.NSTATE = 0 OR (A.NSTATE = 2 AND A.NDOCSORTID = 1)) AND
((((INSTR(‘,’ || A.CPROCUSERLIST || ‘,’,
‘,’ || 31601 || ‘,’) > 0 ) OR
(((27301 = A.RCV_ORGID OR
27301 = A.RCV_ENTITYID) OR
(27301 = A.TEMPORGID OR
27301 = A.TEMPORGID)) AND 20 = A.RCV_ROLEID))) OR
A.NPROCUID = 31601) AND
(A.NMSGID = 0 OR (A.NMSGID IS NOT NULL AND A.NFWQBOPT = 10)) AND
(A.CURTITLE IS NOT NULL) AND
((B.NPROCID = 20 AND A.NPROCSTATUS = 1) OR (B.NPROCID <> 20))
ORDER BY A.DMODIFYDATE DESC;
從業務上看,這條SQL最終的結果集只有幾條記錄,而WF_DOC_GW_SHOUWEN和WF_DOC_GW_FAWEN表的數據量都比較多,有上千萬條,而這兩張表只是為了取字段的內容,沒有過濾任何數據,于是想到,應該把謂詞推入到視圖中,這樣就能用到索引,避免了全表掃描
Sql代碼
SELECT /*+ push_pred(d)*/ ?DISTINCT A.CURTITLE AS CTITLE,
A.DMODIFYDATE,
A.NDOCID AS NDOCID,
A.NPROCID AS NPROCID,
B.CPROCNAME AS CPROCNAME,
B.NDAYS AS TRUE_DAYS,
(SYSDATE – A.DMODIFYDATE) AS DAYSLEFT,
A.NDOCSORTID AS NDOCSORTID,
A.NPROCSTATUS AS NPROCSTATUS,
C.CNAME AS DOCSORTNAME,
NVL(D.NJJCD, 0) NJJCD,
D.CDOCFROM AS CDOCFROM,
D.CDOCPRIORITY AS CDOCPRIORITY,
D.CWENHAO,
A.NFWQBOPT,
D.DW
FROM WF_DOC_GW A,
WF_PROCNAME B,
WF_DOCSORT C,
(SELECT ? NVL(CFWZH, ”) AS CWENHAO,
NVL(CFWDW, ‘ ‘) AS DW,
NDOCID,
NJJCD,
NVL(CDOCFROM, ‘ ‘) AS CDOCFROM,
NVL(CDOCPRIORITY, 0) AS CDOCPRIORITY
FROM WF_DOC_GW_SHOUWEN SW
UNION ALL
SELECT NVL(CWENHAO, ‘ ‘) AS CWENHAO,
NVL(CFWDW, ”) AS DW,
NDOCID,
NJJCD,
NVL(CDOCFROM, ‘本單位發文’) AS CDOCFROM,
NVL(CDOCPRIORITY, 0) AS CDOCPRIORITY
FROM WF_DOC_GW_FAWEN FW) D
WHERE A.NPROCID = B.NPROCID AND
A.NDOCID = D.NDOCID AND
A.NDOCSORTID = C.NDOCSORTID AND
C.NDOCSORTID IN (1, 2) AND
(A.NSTATE = 0 OR (A.NSTATE = 2 AND A.NDOCSORTID = 1)) AND
((((INSTR(‘,’ || A.CPROCUSERLIST || ‘,’,
‘,’ || 31601 || ‘,’) > 0 ) OR
(((27301 = A.RCV_ORGID OR
27301 = A.RCV_ENTITYID) OR
(27301 = A.TEMPORGID OR
27301 = A.TEMPORGID)) AND 20 = A.RCV_ROLEID))) OR
A.NPROCUID = 31601) AND
(A.NMSGID = 0 OR (A.NMSGID IS NOT NULL AND A.NFWQBOPT = 10)) AND
(A.CURTITLE IS NOT NULL) AND
((B.NPROCID = 20 AND A.NPROCSTATUS = 1) OR (B.NPROCID <> 20))
ORDER BY A.DMODIFYDATE DESC
只是加了一個hints /*+ push_pred(d)*/,時間從2秒降到了46毫秒,邏輯讀也降了一半,執行計劃太長,這里就不貼了,本著精益求精的態度,最后應該把中間過程的nvl函數也去掉
總結
以上是生活随笔為你收集整理的oracle hint push_pred,hints的push_pred应用-Oracle的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: oracle字符串只截取中文,Oracl
- 下一篇: linux安装oracle出现os,li