oracle关联视图查询满_对于复杂的SQL, Oracle是怎么做的?
生活随笔
收集整理的這篇文章主要介紹了
oracle关联视图查询满_对于复杂的SQL, Oracle是怎么做的?
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
很多人經常說,同樣的SQL在Oracle中的查詢性能要比在MySQL中好很多,大家有沒有深究過其中的原因呢?除了MySQL 8.0之前不支持hash-join以外,還有其他原因嗎?其實很多時候,出現這種差異的原因,是Oracle有查詢重寫的機制,并不是Oracle本身有多快,而是Oracle聰明的優化器已經幫你改好了SQL。首先,對比下面兩張圖,看看區別在哪里?猜猜為什么會有區別?估計你們是猜不到的。。對比兩個圖,能看到圖2中,oracle做了view merge,將?(select distinct t2.c1,t3.c3 from t2 inner join t3? on (t2.c2 =t3.c2 )) b?打開,view中的表與其他表放在一起計算連接方式,生成一個性能較好的執行計劃;圖1的執行計劃中,外層循環一次,view就要執行一次,里面的謂詞又不高效,因此,查詢性能就表現得很差。就不賣關子了,其實,我在第一次執行SQL前,先將參數?"_complex_view_merging"?設成了false?,默認是true。實驗過程如下:在oracle中,復雜視圖或嵌套視圖(包含有group by 或 distinct)的視圖合并,由_complex_view_merging隱藏參數控制,當設置為true時,優化器評估可能應用視圖合并,但是當設置為false時,即使使用merge hint也不能應用視圖合并。Tips:Oracle優化器真的是很強大,在生產上,最好不要輕易關閉優化器參數。上期分享的案例中的SQL,如果拿到Oracle中執行,因為有查詢重寫的機制,就不會出現執行效率差的現象。(感覺Oracle還是蠻厲害的。。)為了更加突出Oracle優化器的聰明,我在MySQL數據庫中造了一模一樣的數據,把這個sql拿到MySQL數據庫中執行,看看性能如何?sql語句:select * from tt1 inner join(select distinct tt2.c1,tt3.c3 from tt2 inner join tt3 on (tt2.c2 =tt3.c2 )) b on tt1.c1 = b.c1 ;分析執行計劃:首先執行?id=2 子查詢的內容,根據條件“tt2.c2 =tt3.c2” 將表tt2和表tt3關聯,需掃描行數約100000?* 2000;接著執行 id =1 ,將子查詢的結果集和表 tt1 進行關聯,需要掃描的行數約為10 * 2000000?,那么執行這個sql一共需要掃描的行數大約是220,000,000行。執行了17分鐘,結果也沒出來,沒耐心的我直接control + c了。。顯然,MySQL就沒那么聰明了,并沒有幫我們改SQL,規規矩矩的先執行子查詢,再與外表做嵌套連接。模仿Oracle的改寫方式,手動修改了sql文本:select * from tt1 ,(select distinct c2, c1 from tt2) t2 ,(select distinct c2,c3 from tt3) t3where tt1.c1=t2.c1 and t2.c2=t3.c2;執行計劃發生了明顯的改變,掃描的行數也大大減少。執行一次,2.7秒結果就出來了,查詢性能得到了顯著提升。總結:1. 在Oracle數據庫中,絕對不要根據經驗,隨便關閉優化器參數,存在即合理。2. 在MySQL數據庫中,對于多表關聯的SQL查詢,編寫時一定要慎重!
聲明一下,寫這篇文章的目的,不是想說Oracle多好,MySQL多么不好,研發SQL寫得好,那么在MySQL中得查詢性能也是一樣一樣的~
聲明一下,寫這篇文章的目的,不是想說Oracle多好,MySQL多么不好,研發SQL寫得好,那么在MySQL中得查詢性能也是一樣一樣的~
總結
以上是生活随笔為你收集整理的oracle关联视图查询满_对于复杂的SQL, Oracle是怎么做的?的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: tic tac toe php,Pyth
- 下一篇: OpenJudge NOI 1.7 17