【问题标题】:Delete specific rows in Oracle Database using SAS table使用 SAS 表删除 Oracle 数据库中的特定行
【发布时间】:2014-08-27 22:07:47
【问题描述】:

我有一个包含 1M 行的 Oracle 表。我在 SAS 中有一个 oracle 表的子集,其中有 3000 行。我想从 oracle 表中删除这 3000 行。

Oracle Table columns are
Col1    Col2    Col3    timestamp

SAS Table columns are:
Col1    Col2    Col3  

Oracle 表唯一的附加列是时间戳。这是我目前使用的代码,但它需要很多时间。

libname  ora oracle user='xxx' password='ppp' path = abcd;
PROC SQL; 
DELETE from ora.oracle_table a
where exists (select * from sas_table b where a.col1=B.col1 AND a.col2=B.col2 AND A.col3=B.col3 ); 
QUIT;

请告知如何使其更快、更高效。

谢谢!

【问题讨论】:

  • 表有主键吗?
  • 没有。三列组合构成主键。
  • Oracle中col1、2、3是否有联合索引?
  • Oracle中有联合索引。

标签: sql oracle sas


【解决方案1】:

一种选择是将您的 SAS 表推送到 Oracle,然后使用 oracle 端命令执行删除。我不确定 SAS 将如何将上述代码转换为特定于 DBMS 的代码,但它可能会通过网络推送大量数据,具体取决于它如何优化查询;特别是,如果它必须在本地而不是在数据库上执行连接,那将非常昂贵。此外,Oracle 可能可以使用完全本地操作更快地执行删除操作。

IE:

libname ora ... ;

data ora.gtt_tableb;  *or create a temporary or GT table in Oracle and insert into it via proc sql;
set sas_tableb;
run;

proc sql;
 connect to oracle (... );
 execute (
  delete from ... 
  ) by connection to oracle;
quit;

与使用 LIBNAME 连接相比,这可能会显着提高性能。

如果您充分利用 PK 上的索引(如果您还没有该索引),则可能会进一步改进。

【讨论】:

    【解决方案2】:

    @Joe 有一个很好的答案。另一种方法是做这样的事情。这可能允许 libname 引擎将所有工作传递给 Oracle,而不是将行检索回 SAS(这是您的时间去的地方)。

    创建了一些测试数据来展示

    data test1 test2;
    do i=1 to 10;
     do j=1 to 10;
      do k=1 to 10;
       output;
      end;
     end;
    end;
    run;
    
    data todel;
    do i=1 to 3;
     do j=1 to 3;
      do k=1 to 3;
       output;
      end;
     end;
    end;
    run;
    
    proc sql noprint;
    delete from test1 as a
    where a.i in (select distinct i from todel)
      and a.j in (select distinct j from todel)
      and a.k in (select distinct k from todel);
    quit;
    
    proc sql noprint;
    delete from test2 as a
    where exists (select * from todel as b where a.i=b.i and a.j=b.j and a.k=b.k);
    quit;
    

    【讨论】:

      【解决方案3】:

      谢谢你们。 Joe 我采纳了你的建议并编写了这段代码。

       /*---create a temp table in oracle---*/
             libname  ora oracle user='xxx' password='ppp' path = abcd;
              proc append base=ora.TEMP_TABLE data=SAS.sas_TABLE;
              run;
      
              /*-----delete the rows using the temp table--------*/
              proc sql;
               connect to oracle(......);
               execute (delete from ORA.ORACLE_TABLE a
                where exists (select * from ora.TEMP_TABLE b where a.col1=B.col1 AND a.col2=B.col2 AND A.col3=B.col3)
              ) by oracle;
              quit;
      

      非常感谢你们!感谢您的反馈。

      【讨论】:

        猜你喜欢
        • 2019-02-03
        • 2021-12-10
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-12-19
        • 1970-01-01
        相关资源
        最近更新 更多