Oracle for Update SKIP LOCKED and Left Join



目前我正在进行数据库迁移,我需要将下面的查询从Sybase迁移到Oracle,但我真的不知道如何"翻译"。3 . READPAST。有人能帮我吗?

SELECT CC.COURS_CLIENT_ID
, CC.TYPE_CLIENT
, ISNULL( RT1.CODE , RV.CODE) AS CODE 
FROM TB_CLIENT CC READPAST
LEFT JOIN TB_TRANSCO RT1 READPAST 
ON CC.INST_ID = RT1.CONTRAT_ID AND RT1.TRANSCO_ID = 111
LEFT JOIN TB_VAL RV READPAST
ON CC.INST_ID = RV.VAL_ID AND RV.TRANSCO_ID = 111
LEFT JOIN TB_CONT RC 
ON RC.CONTRIB_ID = CC.CONTRIB_ID
WHERE CC.TRT_ID = 123 
AND CC.STATUT = 'STD'
ORDER BY CC.COURS_CLIENT_ID,RT1.CRE_DT

根据Sybase的定义

readpast允许对仅数据锁定的表执行删除命令不会被其他任务持有的不兼容锁阻塞。在数据锁的表,readpast跳过共享的所有行。更新锁或排他锁由另一个任务持有。

在数据页锁定的表中,readpast会跳过所有共享的页。更新锁或排他锁由另一个任务持有。

在您的情况下,如果正在执行select以更新某些记录,您可以使用select for update和选项skip locked

SELECT CC.COURS_CLIENT_ID, CC.TYPE_CLIENT, ISNULL( RT1.CODE , RV.CODE) AS CODE FROM TB_CLIENT CC 
LEFT JOIN TB_TRANSCO RT1 ON CC.INST_ID = RT1.CONTRAT_ID AND RT1.TRANSCO_ID = 111
LEFT JOIN TB_VAL RV ON CC.INST_ID = RV.VAL_ID AND RV.TRANSCO_ID = 111
LEFT JOIN TB_CONT RC ON RC.CONTRIB_ID = CC.CONTRIB_ID
WHERE CC.TRT_ID = 123 AND CC.STATUT = 'STD'
FOR UPDATE SKIP LOCKED; 

然而,对于update skip locked的选择在高并发环境中非常有用,可以防止锁定错误,但是如果更改的值依赖于行中另一列的值,则可能存在逻辑损坏的风险。一般来说,重读策略更好,在更新之前重新读取每一行,以确保自初始读取以来没有更改。

最新更新