即使没有更新行,oracle中的update语句也会保持锁定状态

时间:2013-09-25 16:58:30

标签: oracle11g

如果我在oracle中运行一个更新语句,说“0行更新”,因为它与where子句不匹配而且我没有提交,它是否仍然保持对表的任何protion的锁定?我的猜测是否定的,但我无法证明这一点。

3 个答案:

答案 0 :(得分:0)

在没有更新任何内容的更新后没有保留行锁(毕竟,如果没有行,哪一行应该被锁定?)

您的交易仍然会有一些共享锁(在表上),但那些只是为了防止其他交易改变表。它基本上与select语句在表上获得的“锁定”相同。

From the manual

  

只有在作者修改时才会锁定行。

And further down in the manual

  

行锁,也称为TX锁,是对单行表的锁定。事务为每个修改的行

获取行锁

因此,如果没有更改行,则无法锁定。

答案 1 :(得分:0)

它没有任何锁定。

简单的测试用例

  1. 打开两个oracle会话(sqlplus或sqldeveloper或通过任何其他方式)
  2. 更新table1 where子句(会话1)
  3. 更新table1 where子句(会话2)
  4. 从session1提交(如果存在表锁,则应该挂起)
  5. 从session2提交(如果存在表锁,则此语句将导致死锁)
  6. 条件与行锁定相同(两个会话同时删除同一行)。

答案 2 :(得分:0)

作为documented

  
    

INSERT,UPDATE,DELETE和SELECT ... FOR UPDATE语句的锁定特性如下:

         
        
  • 包含DML语句的事务在由语句修改的行上获取独占行锁。在锁定事务提交或回滚之前,其他事务无法更新或删除锁定的行。

  •     
  • 包含DML语句的事务不需要在子查询或隐式查询选择的任何行上获取行锁,例如WHERE子句中的查询。 DML语句中的子查询或隐式查询保证在查询开始时保持一致,并且不会看到它所属的DML语句的效果。

  •     
  • 事务中的查询可以查看先前DML语句在同一事务中所做的更改,但无法查看在自己的事务之后开始的其他事务的更改。

  •     
  • 除了必要的独占行锁之外,包含DML语句的事务在包含受影响行的表上至少获取一行独占表锁。如果包含的事务已经拥有该表的共享,共享行独占或独占表锁,则不会获取行独占表锁。如果包含的事务已经拥有行共享表锁,则Oracle数据库会自动将此锁转换为行独占表锁。

  •     
  

在更新过程中,表锁是保护表不受更改所必需的,如果更新没有修改任何行,则这是唯一应用的锁。

如果语句对行执行更新而导致该行没有变化(例如,对于date_of_birth已经为空的行,SET DATE_OF_BIRTH = NULL,则仍然会进行行锁定。