我有以下Oracle 10g sql,对我来说看起来是正确的:
update ( select OLD1.TC_CUSTOMER_NUMBER,NEW1.PRD_CUST_NUMBER
FROM TBYC84_PROFILE_ACCOUNT OLD1,
TMP_PRD_KEP NEW1
WHERE
OLD1.TC_CUSTOMER_NUMBER = NEW1.KEP_CUST_NUMBER )
SET
TC_CUSTOMER_NUMBER = PRD_CUST_NUMBER
但是当我运行脚本时,我收到了这个错误:
SQL Error: ORA-01779: cannot modify a column which maps to a non key-preserved table
01779. 00000 - "cannot modify a column which maps to a non key-preserved table"
*Cause: An attempt was made to insert or update columns of a join view which
map to a non-key-preserved table.
*Action: Modify the underlying base tables directly.
我已经对这个错误做过一些研究,但不太确定如何补救。 所以我的问题是,我该如何解决这个问题,还是有更好的方法来编写更新sql?
任何帮助都将不胜感激。
非常感谢的更新 的 我已将更新sql更改为:
update
TBYC84_PROFILE_ACCOUNT PA
set
(
PA.TC_CUSTOMER_NUMBER
) = (
select
TPK.PRD_CUST_NUMBER
from
TMP_PRD_KEP TPK
where
TPK.KEP_CUST_NUMBER = PA.TC_CUSTOMER_NUMBER
)
现在已经更新了TBYC84_PROFILE_ACCOUNT表,并清除了TC_CUSTOMER_NUMBER 柱。 为什么这样做? TBYC84_PROFILE_ACCOUNT.TC_CUSTOMER_NUMBER中可能有多行 具有相同帐号但具有不同user_id的帐号。 请任何人都可以帮助我解决这个问题。 我需要的是将TBYC84_PROFILE_ACCOUNT.TC_CUSTOMER_NUMBER更新为TMP_PRD_KEP中的xrefed,这肯定不是不可能的。
非常感谢答案 0 :(得分:1)
对于UPDATE语句,必须从密钥保留表中提取所有更新的列。
此外:
密钥保留表是基表中的每个主键或唯一键值在连接视图中也是唯一的。
在这种情况下,TBYC84_PROFILE_ACCOUNT
正在更新。因此,它必须在视图的子查询中进行密钥保留。目前它不是。必须通过涉及where子句中的主列或唯一列来进行密钥保留的方式进行更改。如果不可能,您应该尝试更新基表。
<强>更新强>
如果表更新问题,假设子查询最多返回TC_CUSTOMER_NUMBER
列的一个不同值,则获得NULL的原因是所有记录都在更新,即使它们没有任何匹配的记录在TMP_PRD_KEP
表中。因此,父更新语句需要使用where子句:
update
TBYC84_PROFILE_ACCOUNT PA
set
(
PA.TC_CUSTOMER_NUMBER
) = (
select
TPK.PRD_CUST_NUMBER
from
TMP_PRD_KEP TPK
where
TPK.KEP_CUST_NUMBER = PA.TC_CUSTOMER_NUMBER
)
where exists(select *
from TMP_PRD_KEP TPK
where TPK.KEP_CUST_NUMBER = PA.TC_CUSTOMER_NUMBER)
;
答案 1 :(得分:0)
在where子句谓词中使用的列上创建索引。这应该可以解决你的问题。