[英]SQL : Oracle : Optimize LEFT Outer Join Query
我有1個本地表(所有列名與遠程表不同,除了一個)和2個遠程表(具有相同的列名),我需要組合數據。
以下是我使用LEFT OUTER JOIN和UNION編寫的查詢,但性能很慢。
有人可以幫助優化此查詢嗎?
select
"CONTROL_M_SERVER",
"HOST",
CASE
WHEN "AGSTAT" = 'V' THEN 'Available'
WHEN "AGSTAT" = 'U' THEN 'Unavailable'
WHEN "AGSTAT" = 'R' THEN 'Discovering'
ELSE 'Not Defined in Control-M'
END as Agent_Status,
T1.VERSION,
"PORTS",
"MANAGEMENT_IP",
"OPERATING_SYSTEM",
"CLUSTER_ALIAS",
"NODEGROUP",
"APPLICATION_ID",
"DATE_CONFIGURED",
"CONFIGURED_BY"
from "CTMAGENTAUDIT" T1
left outer join (select NODEID,AGSTAT from CMR_NODES@SPDB UNION ALL select NODEID,AGSTAT from CMR_NODES@DEVDB) T2 on T2.NODEID = T1.HOST;
我在查詢中看到的主要問題是CTMAGENTAUDIT
和包含union的子查詢之間的最左邊連接。 該子查詢的問題在於,正如所寫,Oracle不可能使用任何索引進行連接。 這意味着Oracle在加入時可能不得不采用較慢的方法,可能是完整掃描。
這里的一種方法是創建一個包含union查詢的物化視圖,然后將其編入索引:
CREATE MATERIALIZED VIEW T2 AS
SELECT NODEID, AGSTAT FROM CMR_NODES@SPDB
UNION ALL
SELECT NODEID, AGSTAT FROM CMR_NODES@DEVDB;
CREATE INDEX mv_node_idx ON T2 (NODEID);
有了這個索引的物化視圖,我希望您的查詢現在可以更好地執行:
SELECT
CONTROL_M_SERVER,
HOST,
CASE WHEN AGSTAT = 'V' THEN 'Available'
WHEN AGSTAT = 'U' THEN 'Unavailable'
WHEN AGSTAT = 'R' THEN 'Discovering'
ELSE 'Not Defined in Control-M' END AS Agent_Status,
T1.VERSION,
PORTS,
MANAGEMENT_IP,
OPERATING_SYSTEM,
CLUSTER_ALIAS,
NODEGROUP,
APPLICATION_ID,
DATE_CONFIGURED,
CONFIGURED_BY
FROM CTMAGENTAUDIT T1
LEFT OUTER JOIN T2
ON T2.NODEID = T1.HOST;
我會做這樣的事情:
select
"CONTROL_M_SERVER",
"HOST",
CASE
WHEN "AGSTAT" = 'V' THEN 'Available'
WHEN "AGSTAT" = 'U' THEN 'Unavailable'
WHEN "AGSTAT" = 'R' THEN 'Discovering'
ELSE 'Not Defined in Control-M'
END as Agent_Status,
T1.VERSION,
"PORTS",
"MANAGEMENT_IP",
"OPERATING_SYSTEM",
"CLUSTER_ALIAS",
"NODEGROUP",
"APPLICATION_ID",
"DATE_CONFIGURED",
"CONFIGURED_BY",
(select t2.NODEID, t2.AGSTAT from CMR_NODES@SPDB t2 where t1.host = t2.nodeid),
(select t3.NODEID, t3.AGSTAT from CMR_NODES@DEVDB t3 where T1.HOST = T3.NODEID) from t1;
您的查詢基本上是:
select . . .
from CTMAGENTAUDIT T1 left outer join
(select NODEID, AGSTAT
from CMR_NODES@SPDB UNION ALL
select NODEID, AGSTAT
from CMR_NODES@DEVDB
) T2
on T2.NODEID = T1.HOST;
假設NODEID
/ AGSTAT
組合在每個CMR_NODE
表中都是唯一的,我會將其寫成:
select . . .,
coalesce(s1.AGSTAT, s2.AGSTAT) as AGSTAT,
(case coalesce(s1.AGSTAT, s2.AGSTAT)
when 'V' then 'Available'
when 'U' then 'Unavailable'
when 'R' then 'Discovering'
else 'Not Defined in Control-M'
end) as Agent_Status
from CTMAGENTAUDIT T1 left outer join
CMR_NODES@SPDB s1
on s1.NODEID = T1.HOST left outer join
CMR_NODES@DEVDB s2
on s1.NODEID = T1.HOST
這將至少允許每個表單獨優化 - 這應該有所幫助。
顯然,如果您具有設置跨服務器物化視圖的權限和願望,那么具有物化視圖的解決方案將更快。 物化視圖還存在其他維護問題,特別是如果您有多個此類視圖並假設它們同時更新。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.