一個與CONNECT BY相關的BUG
今天遇到一個與CONNECT BY相關的BUG
資料庫版本是solaris 8 + oracle 9204
SQL> SELECT T2.ID
2 FROM Mis2_stat_all T2
3 WHERE t2.plat_id in
4 (SELECT ID FROM (SELECT ID
5 FROM PLT_PLAT MD
6 START WITH ID in
7 (SELECT m.PLAT_ID
8 FROM MIS2_USR_PLAT m, plt_plat p
9 WHERE USER_ID = 'BUSI10000000000098426422'
10 and m.plat_id = p.id
11 and (p.plat_class = '3' or
12 p.id = 'FR20T0000020000000000132'))
13 CONNECT BY PRIOR ID = PLAT_FATHER)
14 )
15 and id=50666180
16 ;
ID
----------
50666180
50666180
Execution Plan
----------------------------------------------------------
0 SELECT STATEMENT Optimizer=CHOOSE (Cost=6 Card=1 Bytes=57)
1 0 NESTED LOOPS (Cost=6 Card=1 Bytes=57)
2 1 TABLE ACCESS (BY GLOBAL INDEX ROWID) OF 'MIS2_STAT_ALL'
(Cost=3 Card=1 Bytes=31)
3 2 INDEX (UNIQUE SCAN) OF 'PK_MIS2_STAT_ALL_ID' (UNIQUE)
(Cost=2 Card=7866838)
4 1 VIEW (Cost=3 Card=1 Bytes=26)
5 4 CONNECT BY (WITH FILTERING)
6 5 NESTED LOOPS
7 6 NESTED LOOPS (Cost=71 Card=6 Bytes=612)
8 7 HASH JOIN (Cost=71 Card=6 Bytes=462)
9 8 TABLE ACCESS (FULL) OF 'PLT_PLAT' (Cost=3 Card
=107 Bytes=2889)
10 8 TABLE ACCESS (FULL) OF 'MIS2_USR_PLAT' (Cost=6
7 Card=6 Bytes=300)
11 7 INDEX (UNIQUE SCAN) OF 'PK_PLT_PLAT' (UNIQUE)
12 6 TABLE ACCESS (BY USER ROWID) OF 'PLT_PLAT'
13 5 HASH JOIN
14 13 CONNECT BY PUMP
15 13 TABLE ACCESS (FULL) OF 'PLT_PLAT' (Cost=3 Card=424
Bytes=21200)
16 5 NESTED LOOPS (Cost=69 Card=1 Bytes=77)
17 16 TABLE ACCESS (BY INDEX ROWID) OF 'PLT_PLAT' (Cost=
2 Card=1 Bytes=27)
18 17 INDEX (UNIQUE SCAN) OF 'PK_PLT_PLAT' (UNIQUE) (C
ost=1 Card=424)
19 16 TABLE ACCESS (FULL) OF 'MIS2_USR_PLAT' (Cost=67 Ca
rd=1 Bytes=50)
這個查詢返回2條資料,但問題是ID是主鍵,不應該返回ID相同的兩條資料。
--下面可以證明ID是主鍵
SQL> SELECT COLUMN_NAME FROM USER_CONS_COLUMNS WHERE constraint_name=(select constraint_name from user_constraints where table_name='MIS2_STAT_ALL' AND CONSTRAINT_TYPE='P');
COLUMN_NAME
------------------------------
ID
這是一個bug,與yangtingkun遇到的問題類似(http://yangtingkun.itpub.net/post/468/106206),但yangtingkun遇到的問題是distinct不起作用,我遇到的問題是主鍵做in操作返回多條相同鍵值的記錄,加了distinct可以解決問題(和yangtingkun遇到的問題相反)。
解決方法有兩種:
1、加distinct
SQL> SELECT T2.ID
2 FROM Mis2_stat_all T2
3 WHERE t2.plat_id in
4 (SELECT ID FROM (SELECT DISTINCT ID
5 FROM PLT_PLAT MD
6 START WITH ID in
7 (SELECT m.PLAT_ID
8 FROM MIS2_USR_PLAT m, plt_plat p
9 WHERE USER_ID = 'BUSI10000000000098426422'
10 and m.plat_id = p.id
11 and (p.plat_class = '3' or
12 p.id = 'FR20T0000020000000000132'))
13 CONNECT BY PRIOR ID = PLAT_FATHER)
14 )
15 and id=50666180
16 ;
ID
----------
50666180
Execution Plan
----------------------------------------------------------
0 SELECT STATEMENT Optimizer=CHOOSE (Cost=12 Card=1 Bytes=57)
1 0 NESTED LOOPS (Cost=12 Card=1 Bytes=57)
2 1 TABLE ACCESS (BY GLOBAL INDEX ROWID) OF 'MIS2_STAT_ALL'
(Cost=3 Card=1 Bytes=31)
3 2 INDEX (UNIQUE SCAN) OF 'PK_MIS2_STAT_ALL_ID' (UNIQUE)
(Cost=2 Card=7866838)
4 1 VIEW (Cost=9 Card=1 Bytes=26)
5 4 SORT (UNIQUE) (Cost=9 Card=424 Bytes=21200)
6 5 CONNECT BY (WITH FILTERING)
7 6 NESTED LOOPS
8 7 NESTED LOOPS (Cost=71 Card=6 Bytes=612)
9 8 HASH JOIN (Cost=71 Card=6 Bytes=462)
10 9 TABLE ACCESS (FULL) OF 'PLT_PLAT' (Cost=3 Ca
rd=107 Bytes=2889)
11 9 TABLE ACCESS (FULL) OF 'MIS2_USR_PLAT' (Cost
=67 Card=6 Bytes=300)
12 8 INDEX (UNIQUE SCAN) OF 'PK_PLT_PLAT' (UNIQUE)
13 7 TABLE ACCESS (BY USER ROWID) OF 'PLT_PLAT'
14 6 HASH JOIN
15 14 CONNECT BY PUMP
16 14 TABLE ACCESS (FULL) OF 'PLT_PLAT' (Cost=3 Card=4
24 Bytes=21200)
17 6 NESTED LOOPS (Cost=69 Card=1 Bytes=77)
18 17 TABLE ACCESS (BY INDEX ROWID) OF 'PLT_PLAT' (Cos
t=2 Card=1 Bytes=27)
19 18 INDEX (UNIQUE SCAN) OF 'PK_PLT_PLAT' (UNIQUE)
(Cost=1 Card=424)
20 17 TABLE ACCESS (FULL) OF 'MIS2_USR_PLAT' (Cost=67
Card=1 Bytes=50)
對比這個執行計劃與前面出錯的可以發現,正確的執行計劃比錯誤的多了 SORT (UNIQUE) 這一步驟。這個BUG就是因為沒有排重而導致返回多條資料。
2、去掉一層無用的巢狀
SQL> SELECT T2.ID
2 FROM Mis2_stat_all T2
3 WHERE t2.plat_id in
4 (SELECT ID
5 FROM PLT_PLAT MD
6 START WITH ID in (SELECT m.PLAT_ID
7 FROM MIS2_USR_PLAT m, plt_plat p
8 WHERE USER_ID = 'BUSI10000000000098426422'
9 and m.plat_id = p.id
10 and (p.plat_class = '3' or
11 p.id = 'FR20T0000020000000000132'))
12 CONNECT BY PRIOR ID = PLAT_FATHER)
13 and id = 50666180;
ID
----------
50666180
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/231499/viewspace-63829/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- 碰到一個latch free相關的BUG
- 分享一個新出爐的JVM裡不痛不癢的BUG(Attach機制相關)JVM
- Connect:一個更好的 gRPCRPC
- 專案管理工具“禪道”與bug相關專案管理
- 一個由public關鍵字引發的bug
- 分享一個 JSON 相關小需求的解決過程與思路JSON
- CSS與中文相關的一些特性CSS
- 一個奇怪的 Bug
- TestHome 的一個 Bug
- Snakeyaml的一個bugYAML
- oracle的一個bugOracle
- 發現了一個關於 gin 1.3.0 框架的 bug框架
- [BUG反饋]兩個關於釋出文章的BUG
- UIView中與AutoLayout相關的幾個方法對比UIView
- 一道與 for 相關的字串面試題字串面試題
- 踩到一個關於分散式鎖的非比尋常的BUG!分散式
- [BUG反饋]get_cover函式相關函式
- [BUG反饋]AdminController類的一個小bugController
- 幾個與文字處理相關的Linux命令總結Linux
- 與數學相關的類
- 發現Mapstruct的一個bugStruct
- 一個排序引發的BUG排序
- 周朝陽:2020年應對風險的十個建議!與每一個人息息相關
- 舒服了,踩到一個關於分散式鎖的非比尋常的BUG!分散式
- 請問我新增一個文件模型一定要建一個相關的表嗎?模型
- 記一個關於std::unordered_map併發訪問的BUG
- 聊一聊JavaScript中的嚴格模式與相關的‘坑’JavaScript模式
- 課時40:類與物件:一些相關的BIF物件
- 一個線上全文索引BUG的排查:關於類阿拉件數字的分詞與檢索索引分詞
- 關於一些奇葩的相容bug
- 關於刪除itunes connect的appAPP
- SpringBoot讀取yml的一個bugSpring Boot
- onethink安裝時的一個bug
- 遭遇ORA-07445 的一個BUG
- 10g sqlplus的一個bugSQL
- 一個關於wait/notify與鎖關係的探究AI
- JVM相關 - StackOverflowError 與 OutOfMemoryErrorJVMError
- MySQL的多層SP中Cursor的m_max_cursor_index相關BUG分析MySqlIndex