如何调用Oracle PL/SQL对象的超级方法

前端之家收集整理的这篇文章主要介绍了如何调用Oracle PL/SQL对象的超级方法前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我想调用一个重写的PL / sql方法.这是一个例子:
-- super class
create or replace type test as object
(
  n number,member procedure proc(SELF in out nocopy test,s varchar2)
)
alter type test not final
/

create or replace type body test is
  member procedure proc(SELF in out nocopy test,s varchar2) is
  begin
    dbms_output.put_line('test1: n='||nvl(self.n,'null')||' s='||s);
    self.n := to_number(s);
  end;
end;
/

-- derived class
create or replace type test2 under test
(
  overriding member procedure proc(SELF in out nocopy test2,s varchar2)
)
/

现在我想调用proc方法的继承版本.当我尝试做一个像treat一样的显式转换(self as test).proc(s);由于PLS-00363,它不会编译:表达式’SYS_TREAT’不能用作赋值目标

当我使用局部变量时,类型体编译:

create or replace type body test2 is
  overriding member procedure proc(SELF in out nocopy test2,s varchar2) is 
    O test;
  begin
    O := treat(self as test);
    O.proc(s);
  end;
end;
/

但是,当我像这样运行我的例子

declare
  obj test2;
begin
  obj := test2(0);
  obj.proc('1');
end;

…它抛出ORA-21780:超过了最大对象持续时间.

有没有办法调用test :: proc(没有序列化/反序列化)?

并且…在调用proc之后,如何将任何已更改的属性(即n)反映在obj中?

更新(谢谢,tbone):

我使用模板方法(‘之前’和’之后’)改变了方法的组织.每当我需要扩展方法时,我都会添加它们.

create or replace type test as object
(
  n number,member procedure proc      (SELF in out nocopy test,s varchar2),member procedure afterProc (SELF in out nocopy test,s varchar2)
  member procedure beforeProc(SELF in out nocopy test,)
not final
/

create or replace type body test is
  member procedure proc(SELF in out nocopy test,s varchar2) is
  begin
    beforeProc(s);
    dbms_output.put_line('test1: n='||nvl(n,'null')||' s='||s);
    n := to_number(s);
    afterProc(s);
  end;
  member procedure afterProc (SELF in out nocopy test,s varchar2) is begin null; end;
  member procedure beforeProc(SELF in out nocopy test,s varchar2) is begin null; end;
end;
/
要访问超级方法,请尝试常规调用或通用表达式.例如,使用人超类型和学生子类型:
CREATE OR REPLACE TYPE person_typ AS OBJECT (
    idno number,name varchar2(30),phone varchar2(20),MAP MEMBER FUNCTION get_idno RETURN NUMBER,MEMBER FUNCTION show RETURN VARCHAR2)
NOT FINAL;

CREATE OR REPLACE TYPE BODY person_typ AS
  MAP MEMBER FUNCTION get_idno RETURN NUMBER IS
  BEGIN
    RETURN idno;
  END;
  MEMBER FUNCTION show RETURN VARCHAR2 IS
  BEGIN
    -- function that can be overriden by subtypes MEMBER FUNCTION show RETURN VARCHAR2 IS BEGIN
    RETURN 'Id: ' || TO_CHAR(idno) || ',Name: ' || name;
  END;
END;

CREATE TYPE student_typ UNDER person_typ (
    dept_id NUMBER,major VARCHAR2(30),OVERRIDING MEMBER FUNCTION show RETURN VARCHAR2)
NOT FINAL;

CREATE TYPE BODY student_typ AS
  OVERRIDING MEMBER FUNCTION show RETURN VARCHAR2 IS
  BEGIN
    RETURN (self AS person_typ).show || ' -- Major: ' || major ;
  END;
END;

-- Using Generalized Invocation
DECLARE
myvar student_typ := student_typ(100,'Sam','6505556666',100,'Math');
name VARCHAR2(100); 
BEGIN
name := (myvar AS person_typ).show; --Generalized invocation 
END;

-- Using Generalized Expression
DECLARE
myvar2 student_typ := student_typ(101,'Math');
name2 VARCHAR2(100); 
BEGIN
name2 := person_typ.show((myvar2 AS person_typ)); -- Generalized expression 
END;

编辑:

如果你是10g,你需要组织一些不同的功能,但是从孩子那里调用super方法功能相同:

CREATE TYPE BODY person_typ AS 
  MAP MEMBER FUNCTION get_idno RETURN NUMBER IS 
  BEGIN
    RETURN idno; 
  END;
  -- static function that can be called by subtypes 
  STATIC FUNCTION show_super (person_obj in person_typ) RETURN VARCHAR2 IS
  BEGIN 
    RETURN 'Id: ' || TO_CHAR(person_obj.idno) || ',Name: ' || person_obj.name;
  END;
  -- function that can be overriden by subtypes 
  MEMBER FUNCTION show RETURN VARCHAR2 IS 
  BEGIN
    RETURN person_typ.show_super ( SELF ); 
  END;
END;

CREATE TYPE student_typ UNDER person_typ ( 
  dept_id NUMBER,OVERRIDING MEMBER FUNCTION show RETURN VARCHAR2) 
  NOT FINAL;

CREATE TYPE BODY student_typ AS 
  OVERRIDING MEMBER FUNCTION show RETURN VARCHAR2 IS 
  BEGIN
    RETURN person_typ.show_super ( SELF ) || ' -- Major: ' || major ;
  END;
END;

现在,您可以通过student方法调用show_super(),或者只调用student方法的show().

从文档中,希望有所帮助.

猜你在找的Oracle相关文章