Sql 永无止境地连接
我在使用Oracle START with/CONNECT BY进行递归时遇到了一些问题 给定一个表Sql 永无止境地连接,sql,oracle,connect-by,Sql,Oracle,Connect By,我在使用Oracle START with/CONNECT BY进行递归时遇到了一些问题 给定一个表id\u string,id,ordre,prec,其中id\u string是id\u ordre的串联。和prec具有相同id的两个元素之间的链接(1_1,1,1,2链接到1_1,1,2,null)。 该表包含500行和196个唯一的id\u字符串 我想从这个表中检索所有链接行,从id_stringequalsid||'| ordre开始,通过ordre和prec链接,我使用以下请求 SELE
id\u string
,id
,ordre
,prec
,其中id\u string
是id\u ordre
的串联。和prec
具有相同id
的两个元素之间的链接(1_1,1,1,2
链接到1_1,1,2,null
)。
该表包含500行和196个唯一的id\u字符串
我想从这个表中检索所有链接行,从id_string
equalsid||'| ordre
开始,通过ordre
和prec
链接,我使用以下请求
SELECT tda.*
FROM T_DRU_ALL tda
START WITH tda.ID|| '_' || tda.ORDRE = tda.id_string
CONNECT BY NOCYCLE PRIOR tda.ORDRE = tda.PREC and tda.id_string = tda.id_string
order by 1,2,3
我的问题很简单,select已经运行了一个小时,现在仍在运行:'(
我肯定我的代码有问题,但我不知道在哪里
数据文件您缺少一个
之前的
,这可能是周期的来源,也是您添加NOCYCLE
的原因;没有它,tda.id\u string=tda.id\u string
总是正确的
所以乍一看,你可以改变:
CONNECT BY NOCYCLE PRIOR tda.ORDRE = tda.PREC and PRIOR tda.id_string = tda.id_string
或删除无循环
:
CONNECT BY PRIOR tda.ORDRE = tda.PREC and PRIOR tda.id_string = tda.id_string
但是,这仍然没有结束;奇怪的是,只是重新排列术语,使其看起来是相同的逻辑结果(但对我来说,无论如何扫描效果更好):
或者重新排列术语(这对我来说比较好,但不应该有任何实际效果——我不知道为什么我认为我之前看到过一个):
现在可以正常工作了:
ID_STRING ID ORDRE PREC
--------- ---------- ---------- ----------
7682_2 7682 2
7682_2 7682 13 2
7682_2 7682 14 13
7690_6 7690 6
7690_7 7690 7
7693_2 7693 2
7693_2 7693 9 2
7693_2 7693 10 9
...
371 rows selected.
就我个人而言,我可能会创造一个开始的条件
START WITH tda.PREC IS NULL
而不是将这些值串联起来——不管怎样,结果与您拥有的数据是相同的
(如果有那么多,您可以在将来提供样本数据;或者提供一个小得多的样本来显示问题…)CONNECT BY是Oracle执行递归的方式。递归发生在函数调用自身直到没有理由调用它时。所以它就像一个循环。问问自己,你的循环有理由退出吗?你可以在APC测试浏览器递归。原始数据包含500行,我使用pastebin来避免FLLOD post:)@如果在表中没有耦合ID PREC,递归就会结束,所以是的,如果我将优先级放在连接的正确部分(tda.ORDRE=preor tda.PREC),它应该停止(但如果没有,我可能会错),它以196行(递归的起点)结束。非常感谢,它完美地解决了我的问题。总结一下答案,问题来自CONNECT BY语句中缺少的Previor,我将它存储在我的脑海中:)
START WITH tda.PREC IS NULL