在 PL/SQL 块中创建 'TABLE AS'

Create 'TABLE AS' in PL/SQL block

我的查询很简单,但 PL/SQL 代码块需要 'INTO' 语句。

这是我的查询:

DECLARE

yesterdays_date DATE := SYSDATE-1;
start_date DATE :='01/JAN/2013';

BEGIN     
     EXECUTE IMMEDIATE 'DROP TABLE P2P_DATA'; 
    EXCEPTION     
  WHEN OTHERS THEN         
   IF SQLCODE != -942 THEN     
 --if table not found DO NOTHING AND MOVE ON
 --dbms_output.put_line('HELLO');
            NULL;
    END IF;

---------------------------create new table here-------------------
CREATE TABLE P2P_DATA AS
SELECT 
    GM_NAME,
    NEW_SKILL,    
    WEEK_DATE,
    TOR_MWF
FROM TEST_TABLE 
WHERE WEEK_DATE BETWEEN start_date AND yesterdays_date;

END;

它给出了编译时间错误:

FOUND CREATE: EXPECTING END SELECT or (BEGIN CASE CLOSE CONTINUE DECLARE ... ETC)

我只是在声明块中设置日期,然后创建一个新的 table 作为 select 语句的结果。有什么想法可以完成这项任务吗?

这做同样的事情,但避免了立即执行和创建和删除 tables 的开销。

DECLARE

yesterdays_date DATE := SYSDATE-1;
start_date DATE :='01/JAN/2013';

BEGIN     
 --clear out old data------
 DELETE from P2P_DATA;

---------------------------insert new data here-----------------
INSERT INTO P2P_DATA
SELECT 
GM_NAME,
CASE WHEN SUBSTR(CST_NAME,0,5) = 'A' 
     THEN 'BVG1' ELSE SUBSTR(CST_NAME,0,5) END AS CST_NAME,
NEW_SKILL,    
WEEK_DATE,
TOR_MWF,
TOR_MA,    
TOR_DL
FROM TEST_TABLE 
WHERE WEEK_DATE BETWEEN start_date AND yesterdays_date;

END;

--以防万一

如果您只需要一个子集,最好只创建一个视图并避免整个 table 事情。

CREATE VIEW VW_P2P_DATA 
AS
SELECT 
GM_NAME,
CASE WHEN SUBSTR(CST_NAME,0,5) = 'A' 
     THEN 'BVG1' ELSE SUBSTR(CST_NAME,0,5) END AS CST_NAME,
NEW_SKILL,    
WEEK_DATE,
TOR_MWF,
TOR_MA,    
TOR_DL
FROM TEST_TABLE 
WHERE WEEK_DATE BETWEEN TO_DATE('01/JAN/2013','DD/MON/YYYY') AND SYSDATE-1;

您不能在 PL/SQL 块内进行 DDL 查询;如果你需要这样做,你必须使用 dinamic SQL;例如,您可以使用:

execute immediate '
                    CREATE TABLE P2P_DATA AS
                    SELECT 
                        GM_NAME,
                        NEW_SKILL,    
                        WEEK_DATE,
                        TOR_MWF
                    FROM TEST_TABLE 
                    WHERE WEEK_DATE BETWEEN start_date AND yesterdays_date;
                    ';

但是,如果可以的话,请考虑与 create/drop 表不同的解决方案

实际上,我会将其作为答案而不是评论...

我建议完全避免 PL/SQL ...只需执行以下操作:

  truncate table P2P_DATA;

  insert into P2P_DATA
     SELECT 
      GM_NAME,
      NEW_SKILL,    
      WEEK_DATE,
      TOR_MWF
  FROM TEST_TABLE 
  WHERE WEEK_DATE BETWEEN to_date('01/JAN/2013','dd/MON/yyyy') AND SYSDATE-1;

更简单、更干净、更快。 ;)