部分更新在过程中不起作用
Posted
技术标签:
【中文标题】部分更新在过程中不起作用【英文标题】:Part of the update is not working in Procedure 【发布时间】:2017-03-10 10:17:10 【问题描述】:我在我的程序中写了两个更新语句。出于某种奇怪的原因,第一个更新语句只更新了一些记录(基本上我更新了超过 100,000 行)。所以第二个更新语句一直工作正常。我集思广益,但程序成功完成,但我不知道是什么问题。有什么方法可以进行验证检查,比如有多少更新了,有多少没有更新?
第一次更新声明(有时只更新部分记录)
UPDATE /*+PARALLEL(A,10,2)*/ VV_ACT_CALL_DET_DIS_EXTRACT A SET PRIORITY =
( SELECT P.PRIORITY
FROM VV_ACT_CALL_DET_DIS P
WHERE P.CALL_ID = A.CALL_ID
AND P.PRODUCT_ID = A.PRODUCT_ID
AND P.IS_DELETED = A.IS_DELETED
AND ROWVAL = 1 )
WHERE EXTRACT_STATUS = 'PENDING'
AND EXISTS
( SELECT B.PRIORITY
FROM VV_ACT_CALL_DET_DIS B
WHERE B.CALL_ID=A.CALL_ID
AND B.PRODUCT_ID = A.PRODUCT_ID
AND B.IS_DELETED = A.IS_DELETED );
第二次更新语句,虽然条件同上,但始终成功更新记录
UPDATE /*+PARALLEL(A,10,2)*/ VV_ACT_CALL_DET_DIS_EXTRACT A SET TYPE =
( SELECT P.TYPE_VAL
FROM VV_ACT_CALL_DET_DIS P
WHERE P.CALL_ID = A.CALL_ID
AND P.PRODUCT_ID = A.PRODUCT_ID
AND P.IS_DELETED = A.IS_DELETED
AND ROWVAL = 1 )
WHERE EXTRACT_STATUS = 'PENDING'
AND EXISTS
( SELECT B.TYPE_VAL
FROM VV_ACT_CALL_DET_DIS B
WHERE B.CALL_ID = A.CALL_ID
AND B.PRODUCT_ID = A.PRODUCT_ID
AND B.IS_DELETED = A.IS_DELETED );
【问题讨论】:
update ... set (TYPE, PRIORITY)=(SELECT P.TYPE_VAL, P.PRIORITY ...)
它是相同的 Rene,只是我首先更新了优先级字段,然后我更新了类型字段
@Mike 是的,会尝试这样做,但如果您分享任何关于验证检查的想法会有所帮助
@Milaci EXISTS
返回一行的存在,返回值无所谓。 exists(select type_val)
、exists(select priority)
和 exists(select 1)
相同
@ShankarPanda 您正在更新具有相同条件的两个字段,只需在单个更新语句中执行。不要做两次你可以做一次的事情。您将生成双倍的重做。 “有什么方法可以进行验证检查,比如有多少更新了,有多少没有更新?”如果您在 PL/SQL 中执行此操作,您将不会收到任何反馈,但如果您在 PL/SQL 中执行此操作,SQL%ROWCOUNT 会为您提供您更新的记录数。
【参考方案1】:
您可以在更新语句之后(提交之前)使用 SQL%rowcount 查询更新的行数,例如:
update ....
if sql%rowcount <> nnn then --or = 0 or ...
raise_application_error(-20001, 'invalid number of rows updated: ' || sql%rowcount);
end if;
关于“为什么不更新问题”:没有看到实际数据很难说。你能给我们一个示例数据集吗?第一条语句是否有可能更新相同数量的行,但数据没有改变(优先级保持不变)?
【讨论】:
当然,错误消息也可能会说“没有找到更新的任何内容”或其他内容。除了 0,您还期望sql%rowcount
的哪些值?
也许 OP 想测试两个更新语句是否影响相同数量的行,也许只有 0 是有趣的。这只是一个例子,但为了更清楚,我正在编辑它。 .以上是关于部分更新在过程中不起作用的主要内容,如果未能解决你的问题,请参考以下文章