2012-03-29 5 views
5

オブジェクト型に引数なしのコンストラクタがありますが、その型の列のデフォルト値として指定すると、ORA-00904:無効な識別子エラーが発生します。Oracle:オブジェクト型列のデフォルト値を指定する

例:

 
CREATE OR REPLACE TYPE test_t AS OBJECT 
(
    val  NUMBER(10), 
    CONSTRUCTOR FUNCTION test_t return self as result 
) 

CREATE OR REPLACE TYPE BODY test_t AS 
    CONSTRUCTOR FUNCTION test_t RETURN SELF AS RESULT IS 
    BEGIN 
    val := 1; 
    RETURN; 
    END; 
END; 

CREATE TABLE test_table (
    test_attr test_t DEFAULT new test_t() 
) 

Error: ORA-00904: "INKA"."TEST_T"."TEST_T": invalid identifier 

私は、例えばでDEFAULTを交換した場合test_t(1)、それは動作しますが、OOカプセル化パラダイムを破るようなことは、同じタイプのすべてのフィールドに同じデフォルトの「デフォルト値」を設定したいのですが:-)

私はありませんここに何か、またはこれは普通で、このようなデフォルト以外のコンストラクタを使うことはできませんか?

答えて

0

このようには見えません。

回避策の一つは、トリガーを使用することです:

CREATE OR REPLACE TRIGGER test_trigger 
    BEFORE INSERT OR UPDATE 
ON test_table 
    FOR EACH ROW 
WHEN (new.test_attr IS NULL) 
BEGIN 
    :new.test_attr := NEW test_t(); 
END test_trigger; 
/
それは完全に

CONSTRUCTOR FUNCTION test_t(in_val NUMBER) 
RETURN SELF AS RESULT 

がにつながるデフォルトコンストラクタをオーバーライドし、途中でデフォルト以外のコンストラクタを無視しない


DEFAULT NEW test_t(1)で表を定義しようとすると例外:

ORA-06553:PLS-307: 'TEST_T' は、このコールに一致する

+0

ORA-06553のあまりに多くの宣言:PLS-307が重複コンストラクタ定義の結果であり、Oracleはその中に多少面白いです。 「in_val」パラメータ名をval(属性の名前と同じ)に置き換えると、デフォルトのコンストラクタが正しく上書きされます。 –

+0

しかし、それでもこのコンストラクタが見つかりました... –

+0

私はトリガーの回避策を認識していますが、もっと読みやすく管理しやすい方法で可能なコードの5-10行です。最初は、SQL文脈がPL/SQL文脈の中に見えないので、それは不可能であると推測しましたが、OOのどれも純粋なSQLで動作しないので、明らかにそうではありません。したがって、この問題は、Oracleの部分の監視、または私が認識していないいくつかの構文があります... –

関連する問題