使用 PL/SQL 根据 Oracle SQL 中的父项更新子计数器
Posted
技术标签:
【中文标题】使用 PL/SQL 根据 Oracle SQL 中的父项更新子计数器【英文标题】:Update child counter based on parent in Oracle SQL using PL/SQL 【发布时间】:2022-01-06 09:21:51 【问题描述】:我有两张桌子Invoice
和InvoiceLine
。 Invoice
是父级,InvoiceLine
是子级。
表InvoiceLine
有一个列lineNr
,它应该存储基于父表的值。因此,例如 invoice1 应具有 lineNr 1、2、3 等... Invoice2 也应具有 lineNr 1、2、3 等...
现在lineNr
是错误的,因为无论父表Invoice
都创建了计数器,因此例如 invoice2 的 lineNr 为 4、5、6...等。
如何使用 PL/SQL 修复 InvoiceLine
表中的行计数器?
有人可以帮帮我吗?我认为需要一个循环。
【问题讨论】:
minimal reproducible example 在询问 SQL 问题时是一个很好的开始。 【参考方案1】:按照你的描述,“父子”关系是假的。您应该在数据库中做到这一点,而不是在纸上(或在您的想法中)。
因为,如果它们真的是父子表,就会有一个参照完整性约束,不允许您输入无效值(即子表不可能有父子表中不存在的 linenr
值表)。
应该是这样的:
SQL> create table invoice
2 (linenr number constraint pk_inv primary key,
3 whatever varchar2(10)
4 );
Table created.
SQL> create table invoiceline
2 (id_invline number constraint pk_invline primary key,
3 linenr number constraint fk_invline_inv references invoice(linenr),
4 whatever varchar2(2)
5 );
Table created.
SQL>
我推测linenr
列做了外键约束。
或者,可能是复合主键(然后是外键):
SQL> create table invoice
2 (id_inv number,
3 linenr number,
4 whatever varchar2(10),
5 --
6 constraint pk_inv primary key (id_inv, linenr)
7 );
Table created.
SQL> create table invoiceline
2 (id_invline number constraint pk_invline primary key,
3 id_inv number,
4 linenr number,
5 whatever varchar2(2),
6 --
7 constraint fk_invline_inv foreign key (id_inv, linenr)
8 references invoice (id_inv, linenr)
9 );
Table created.
SQL>
现在该怎么办?谁知道?您如何知道将哪些行更改为哪些值?也许使用update
声明如下:
update invoiceline b set
b.linenr = (select a.linenr
from invoice a
where a.id_inv = b.id_inv
)
where exists (select null
from invoice c
where c.id_inv = b.id_inv
);
如果你想知道“为什么是exists
?”,答案是:因为那种假父子关系。不能保证每个子行都有其父行,因此要避免为没有父行的行将 linenr
设置为 NULL
。
【讨论】:
以上是关于使用 PL/SQL 根据 Oracle SQL 中的父项更新子计数器的主要内容,如果未能解决你的问题,请参考以下文章
根据 Oracle 10g PL/SQL 中的内容将行转为列