嘿,大家在这里看看你们是否可以帮助我解决我遇到的过程问题。长话短说,我做了一张新桌子,叫做
Create Table ClientHistoricalPurchases(
ClientID varchar2(6) constraint clientidhistorical references Clients,
DistinctProducts number (9),
TotalProducts number(9),
TotalCost number (9,2),
Primary Key (ClientID));
我想通过运行主要从下表读取的过程来填充/更新此表:
create table OrderDetails(
OrderID varchar2(6) CONSTRAINT orddetpk PRIMARY KEY,
ProductID varchar2(6) CONSTRAINT prdfk REFERENCES Products ,
UnitPrice number(10,2),
Quantity number(4),
Discount number(3),
ShippingDate date);
我使用另外两个称为Orders和Clients的表进行了几次联接,但是这些联接是使用主键/ FK进行的简单联接。
因此,此过程的目标是,当我运行该过程时,我想遍历订单详细信息,并要计算客户购买的产品的不同数量,总产品和总购买金额,并且我想更新如果新记录不在新ClientHistoricalPurchases表中,则该记录具有新值,如果不存在,我想为其添加新记录。所以这是我写的,但给我错误:
Create or Replace Procedure Update_ClientHistPurch as
Cursor C1 is
Select orderid, orders.clientid, productid, unitprice, quantity, discount
from orderdetails
Inner join orders on orderdetails.orderid = orders.clientid
for update of TotalCost;
PurchaseRow c1%RowType;
DistinctProducts orderdetails.quantity%type;
TotalProducts orderdetails.quantity%type;
ProposedNewBalance orderdetails.unitprice%type;
Begin
Begin
Begin
Begin
Open C1;
Fetch c1 into PurchaseRow;
While c1% Found Loop
Select count(distinct productid)
into DistinctProducts
from orderdetails
Inner join orders on orderdetails.orderid = orders.orderid
Inner join clients on orders.clientid = clients.clientid
where clients.clientid = purchaserow.clientid;
end;
Select count(ProductID)
into TotalProducts
from orderdetails
Inner join orders on orderdetails.orderid = orders.orderid
Inner join clients on orders.clientid = clients.clientid
where clients.clientid = purchaserow.clientid;
end;
Select sum((unitprice * quantity) - discount)
into ProposedNewBalance
from orderdetails
Inner join orders on orderdetails.orderid = orders.orderid
Inner join clients on orders.clientid = clients.clientid
where clients.clientid = purchaserow.clientid;
end;
If purchaserow.clientid not in ClientHistoricalpurchases.clientid then
insert into ClientHistoricalPurchases values (purchaserow.clientid,DistinctProducts, TotalProducts, ProposedNewBalance);
End if;
If purchaserow.clientid in ClientHistoricalPurchases.clientid then
Update Clienthistoricalpurchases
set clienthistoricalpurchases.distinctproducts = distinctproducts, clienthistoricalpurchases.totalproducts = totalproducts, clienthistoricalpurchases.totalcost = ProposedNewBalance
where purchaserow.clientid = clienthistoricalpurchases.clientid;
end if;
end loop;
end;
以下是错误:
错误(27,4):PLS-00103:遇到符号“;”当期待一个 以下内容:循环用符号“循环”代替“;”。 继续。
错误(33,7):PLS-00103:遇到符号“ JOIN” 当期望以下之一时:对于有 相交的减号在连接处开始合并
任何帮助都是值得赞赏的家伙。谢谢!
答案 0 :(得分:2)
除了已经给您的评论和答案之外,我相信您已经使程序过于复杂。您正在非常有步骤地进行操作,而不是按照应有的方式进行思考。您还可以在三个基本相同的查询(例如,相同的表,联接条件和谓词)中获得汇总列-您可以将它们全部组合在一起,以在单个查询中获得三个结果。
如果该客户的行尚不存在,您似乎正在尝试将其插入到clienthistoricalpurchases表中,否则您将更新该行。那立即向我尖叫“合并声明”。
结合所有这些,我认为您当前的过程应该只包含一个合并语句:
MERGE INTO clienthistoricalpurchases tgt
USING (SELECT clients.client_id,
COUNT(DISTINCT od.productid) distinct_products,
COUNT(od.productid) total_products,
SUM((od.unitprice * od.quantity) - od.discount) proposed_new_balance
FROM orderdetails od
INNER JOIN orders
ON orderdetails.orderid = orders.orderid
INNER JOIN clients
ON orders.clientid = clients.clientid
GROUP BY clients.client_id) src
ON (tgt.clientid = src.client_id)
WHEN NOT MATCHED THEN
INSERT (tgt.clientid,
tgt.distinctproducts,
tgt.totalproducts,
tgt.totalcost)
VALUES (src.clientid,
src.distinct_products,
src.total_products,
src.proposed_new_balance)
WHEN MATCHED THEN
UPDATE SET tgt.distinctproducts = src.distinct_products,
tgt.totalproducts = src.total_products,
tgt.totalcost = src.proposed_new_balance;
但是,我对您当前的逻辑和/或数据模型有些担心。
您似乎希望每个clientid最多出现一行在clienthistoricalpurchases中。如果一个clientid有两个或多个不同的订单怎么办?当前,您将覆盖任何现有行。
此外,您是否真的想在每次运行订单时在所有订单上应用此逻辑?
答案 1 :(得分:0)
代码的第28行,即END
之后的第一个WHILE
应该是END LOOP