【问题标题】:Interaction of SELECT FOR UPDATE lock with cursor and batch DMLSELECT FOR UPDATE 锁与游标和批处理 DML 的交互
【发布时间】:2018-05-30 15:40:22
【问题描述】:

目前我的代码框架如下:

varchar rowidvariable[batchlimitcount][19];

stmt = "Select rowid from table_name where xx"
delstmt = "delete from table_name where rowid=:rowidvariable"
prepare delstatement using delstmt;

prepare cursor from stmt;
declare cursor from preparecursor;
open cursor;

while(1)
{
    fetch cursor into rowidvariable;

    somecondition {break};        

    exec sql for fetchedCount 
        execute delstatement using :rowidvariable;

    commit;

} 

有人向我指出,使用 SELECT FOR UPADATE 锁定表将是确保 100% 锁定行并且 ROWID 在任何情况下(无论机会多么小)都不会改变的方法.

但是,由于commit; 释放了锁,而且由于有数百万条记录,我确实批量删除非常重要,因此在推进所提出的解决方案方面似乎存在挑战。

如果有更好的选择,请告知。提前致谢。

参考我之前的问题:Link

请注意,整个过程都在 oracle-pro-c 中进行。

【问题讨论】:

  • 您能否详细说明您的代码。当然,使用 ROWID 是访问表中行的最快方法,但它仍然是逐行处理,默认情况下很慢。目前我看不出有任何理由使用循环(或批量处理)。尝试将所有条件放在一个 DELETE 语句中,这应该是最好的。
  • @WernfriedDomscheit 问题是,这种类型的清除不是一次性的过程,在一次删除许多记录时,它可能会一次创建很多撤消,这可能会使数据库瘫痪。因此,批处理如此少的行被删除和提交,从而减少了系统负担。

标签: oracle oracle-pro-c


【解决方案1】:

听起来问题是您必须删除数百万行,因此您想分批进行

如果是这样,这可能对您有用 - 它会循环遍历并删除行并提交,这样您就不会用尽撤消操作,也不必担心锁定行

begin
   loop
      delete from xx where yyy=zzz and rownum < 1000;
      exit when sql%rowcount = 0;
      commit;
   end loop;
   commit;
end;
/

【讨论】:

  • 正如问题中正确指出的那样,COMMIT 释放行锁,因此您不应将其与ROWID 一起使用
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-02-21
  • 2014-03-10
  • 1970-01-01
  • 1970-01-01
  • 2011-06-28
相关资源
最近更新 更多