2017-06-16 8 views
0

I 2列のテーブルTSK有する:数のタスクID、等であり得るXMLTYPEでタスクスコープ:オラクルXMLEXISTS

<scope> 
    <siteCode>2</siteCode> 
    <supplierCode>1111</supplierCode> 
    <contractCode>464</contractCode> 
    <orderNumber>85235478</orderNumber> 
</scope> 

しかし、タグの下の要素は異なっていてもよいし1レコードを別のレコードに変更する

範囲内のいくつかの条件に一致するタスクIDを選択する必要があります。例えば :範囲として

select tskid 
from tsk t 
where xmlexists('$a/scope[siteCode = 2 and supplierCode = 111]' passing t.tskscope as "a"); 

は変更になる場合があり、IはVARCHAR2型で、探すために、XMLパスp_xmlpathをとるPL/SQLの機能を有しています。 だから例えば、p_xmlpathは次のようになります。

p_xmlpath := 'scope[siteCode = 2 and supplierCode = 1111]'; 

それから私は、一致するレコードを検索するXMLEXISTSでクエリを実行します。 私は、次のようにバインド変数でそれを行うために考えた:

select tskid 
from tsk t 
where xmlexists('$a/$b' passing t.tskscope as "a", p_xmlpath as "b"); 

をこのようにすることで、クエリは、XMLEXISTSで条件を取ることなく、すべてのレコードを返します。

誰かがこれを管理する方法、つまりXMLEXISTSに与える変数パスを知っていますか?

追加情報:今まで、私は、関数existsNodeを使用し、次のクエリは正しく仕事をしていました:

select tskid 
from tsk t 
where existsnode(t.tskscope, p_xmlpath) = 1; 

しかし一方でいるexistsNodeは廃止され、他に私は気づいた私の状況で関数xmlexistsはexistsNodeよりもはるかに高速だったので、私はxmlexistsに切り替えるでしょう。

ありがとうございます。

答えて

0

私はあなたができるとは思わない。それは、検索値が変数であり、検索条件全体ではないように見えるだけです。

select tskid 
from tsk t 
where xmlexists(replace('$a/$b', '$b', p_xmlpath) passing t.tskscope as "a"); 

または変数としてXPath文字列を構築しますが、むしろそこに置き換える必要があり、かつ$a/一部が含まれていませたければ:あなたはreplace()でruntomeでXPathを構築することができ、回避策として

p_xmlpath := '$a/' || p_xmlpath; 

select tskid 
from tsk t 
where xmlexists(p_xmlpath passing t.tskscope as "a"); 
+0

ありがとうございます!私は変数として全体のパスを定義して解決策を試してみて、それは私に正しい結果を与えます。残念ながら、クエリはリテラル文字列の同じパスで実行した場合よりも200倍長くなりますが、理由はありません... – cbe