我想在10gR2中实现堆栈数据结构。
然而,当我尝试做的时候:
创建或替换XDB.DBMS_XMLDOM.DOMNODE的TYPE ContainerArray AS VARRAY(25);
我得到了
“架构级别类型具有对XDB.DBMS_XMLDOM的非法引用。”
所以我发现这是因为Oracle不会让你创建引用包级别类型的模式级类型。
我可以通过在包中创建类型来解决这个问题:
TYPE ContainerArray AS VARRAY(25) OF XDB.DBMS_XMLDOM.DOMNODE;
然而,当我尝试创建我的对象时,我无法引用包级别类型:
CREATE TYPE DOMNode_Stack AS OBJECT (
max_size INTEGER,
top INTEGER,
position ContainerArray,
MEMBER PROCEDURE initialize,
MEMBER FUNCTION full RETURN BOOLEAN,
MEMBER FUNCTION empty RETURN BOOLEAN,
MEMBER PROCEDURE push (n IN INTEGER),
MEMBER PROCEDURE pop (n OUT INTEGER)
);
我无法在包内创建对象类型,因为我得到了
“此上下文不支持对象。”
有关如何解决此问题的任何想法?
答案 0 :(得分:1)
像OBJECT这样的sql级对象只能在其属性中引用SQL类型。
如果你看到包规范:
TYPE DOMNode IS RECORD (id RAW(13));
所以你可以创建一个
的sql数组SQL> CREATE or replace TYPE ContainerArray AS VARRAY(25) OF raw(13);
2 /
Type created.
然后在你的对象放置
position ContainerArray
哪个会奏效。当你引用它时,只需分配一个局部变量 v_dom xml_dom.domnode; 开始 v_dom.id:=您当时正在处理的数组索引值;
请注意,在任何Oracle升级中,您需要验证DOMNODE的结构是否未发生更改。
编辑:这是一个示例:
SQL> set serverout on
SQL> create or replace type containerarray as varray(25) of raw(13);
2 /
Type created.
SQL> create type domnode_stack as object (
2 position containerarray,
3 member procedure initialize,
4 member procedure print_node_names
5 );
6 /
Type created.
SQL> CREATE TYPE body DOMNode_Stack
2 as
3 member procedure initialize
4 is
5 v_dom dbms_xmldom.DOMNode;
6 v_doc dbms_xmldom.domdocument;
7 v_nl dbms_xmldom.DOMNodeList;
8 begin
9 position := containerarray();
10 v_doc := dbms_xmldom.newDOMDocument(xmltype('<root><foo>test</foo><foo2>test2</foo2></root>')); -- just some summy data.
11 v_nl := dbms_xmldom.getElementsByTagName(v_doc, '*');
12 for idx in 0..dbms_xmldom.getLength(v_nl)-1 loop
13 v_dom := DBMS_XMLDOM.item(v_nl, idx);
14 position.extend;
15 position(position.last) := v_dom.id;
16 end loop;
17 end;
18
19 member procedure print_node_names
20 is
21 v_dom dbms_xmldom.DOMNode;
22 begin
23 for idx in 1..position.count
24 loop
25 v_dom.id := position(idx);
26 dbms_output.put_line(dbms_xmldom.getnodename(v_dom)||'='||dbms_xmldom.getnodevalue(dbms_xmldom.getfirstchild(v_dom)));
27 end loop;
28 end;
29 end;
30 /
Type body created.
SQL> show errors type body DOMNode_Stack
No errors.
SQL> declare
2 o_domnode DOMNode_Stack := DOMNode_Stack(null);
3 begin
4 o_domnode.initialize();
5 o_domnode.print_node_names();
6 end;
7 /
root=
foo=test
foo2=test2
PL/SQL procedure successfully completed.
重要的一点是:
从DBMS_XMLDOM分配给sql类型我们采用v_dom.id。
13 v_dom:= DBMS_XMLDOM.item(v_nl,idx); 14位置。扩展; 15 position(position.last):= v_dom.id;
和倒车时:
23表示1..position.count中的idx 24循环 25 v_dom.id:= position(idx);
即分配ID部分(不是记录本身......会出错)。