2013-02-08 69 views
1

下面是確定表是否存在然後刪除/創建表的PL/SQL腳本。如果它不存在,反正創建表。所以,當我跑的劇本,我收到了以下:如何使用EXECUTE IMMEDIATE語句糾正PL/SQL腳本中的ORA-00904錯誤?

ORA-00904:「E」:無效的標識符

我認爲語法準確和雙引號「E」是正確,但顯然,不是。請指教。

謝謝。

DECLARE 

    l_cnt NUMBER; 

BEGIN 
    SELECT COUNT(*) 
    INTO l_cnt 
    FROM dba_tables 
    WHERE owner = 'ABCD' 
    AND table_name = 'SEC_REC_TEMP'; 

    IF(l_cnt > 0) 
    THEN 
    EXECUTE IMMEDIATE 'DROP TABLE sec_rec_temp'; 
    EXECUTE IMMEDIATE 'CREATE TABLE sec_rec_temp 
         AS 
         SELECT is.inv_num 
          FROM abcd.inv_summ is 
           ,abcd.bill_fee bf 
         WHERE is.inv_num = bf.inv_num 
          AND trim(bf.fee_type) = "E" 
         GROUP BY is.inv_num'; 
    ELSE 
    EXECUTE IMMEDIATE 'CREATE TABLE sec_rec_temp 
         AS 
         SELECT is.inv_num 
          FROM abcd.inv_summ is 
           ,abcd.bill_fee bf 
         WHERE is.inv_num = bf.inv_num 
          AND trim(bf.fee_type) = "E" 
         GROUP BY is.inv_num'; 
    END IF; 
END; 
/

回答

3

首先,刪除並重新創建表的PL/SQL腳本非常值得懷疑。例如,你真的確定你不想創建一個定期刷新的物化視圖嗎?在PL/SQL中執行DDL幾乎總是一個糟糕的方法。如果您可以解釋您正在嘗試解決的業務問題,那麼我們可以向您提供更好的技術解決方案。其次,如果你想在PL/SQL中的字符串中單引號轉義,你需要使用兩個連續的單引號。沒有一個雙引號字符。

DECLARE 
    l_cnt NUMBER; 
BEGIN 
    SELECT COUNT(*) 
    INTO l_cnt 
    FROM dba_tables 
    WHERE owner = 'ABCD' 
    AND table_name = 'SEC_REC_TEMP'; 

    IF(l_cnt > 0) 
    THEN 
    EXECUTE IMMEDIATE 'DROP TABLE sec_rec_temp'; 
    EXECUTE IMMEDIATE 'CREATE TABLE sec_rec_temp 
         AS 
         SELECT is.inv_num 
          FROM abcd.inv_summ is 
           ,abcd.bill_fee bf 
         WHERE is.inv_num = bf.inv_num 
          AND trim(bf.fee_type) = ''E'' 
         GROUP BY is.inv_num'; 
    ELSE 
    EXECUTE IMMEDIATE 'CREATE TABLE sec_rec_temp 
         AS 
         SELECT is.inv_num 
          FROM abcd.inv_summ is 
           ,abcd.bill_fee bf 
         WHERE is.inv_num = bf.inv_num 
          AND trim(bf.fee_type) = ''E'' 
         GROUP BY is.inv_num'; 
    END IF; 
END; 

或者,您可以用q引用語法

DECLARE 
    l_cnt NUMBER; 
BEGIN 
    SELECT COUNT(*) 
    INTO l_cnt 
    FROM dba_tables 
    WHERE owner = 'ABCD' 
    AND table_name = 'SEC_REC_TEMP'; 

    IF(l_cnt > 0) 
    THEN 
    EXECUTE IMMEDIATE 'DROP TABLE sec_rec_temp'; 
    EXECUTE IMMEDIATE q'[CREATE TABLE sec_rec_temp 
         AS 
         SELECT is.inv_num 
          FROM abcd.inv_summ is 
           ,abcd.bill_fee bf 
         WHERE is.inv_num = bf.inv_num 
          AND trim(bf.fee_type) = 'E' 
         GROUP BY is.inv_num]'; 
    ELSE 
    EXECUTE IMMEDIATE q'[CREATE TABLE sec_rec_temp 
         AS 
         SELECT is.inv_num 
          FROM abcd.inv_summ is 
           ,abcd.bill_fee bf 
         WHERE is.inv_num = bf.inv_num 
          AND trim(bf.fee_type) = 'E' 
         GROUP BY is.inv_num]'; 
    END IF; 
END; 
2

你需要用另一個單引號

AND trim(bf.fee_type) = ''E'' 
逃單引號