我是PL / SQL编程的新手,我遇到了解决这个问题的问题:
问题陈述:
→EMPLOYEE_PAY表包含列(ID,NAME,LOCATION,BASIC_SALARY,NET_SALARY)。
公司对所有员工都有相同基本工资的政策,但净工资根据员工的表现而变化。因此,Basic Salary列必须始终具有相同的值。要求是
净工资可以更新为 -
新净工资=新基本工资*(旧净工资/旧基本工资)
例:
EMPLOYEE TABLE
ID NAME LOCATION BASIC_SALARY NET_SALARY
的 _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __
12102 John Bangalore 10000 25450
12155 Rana Hyderabad 10000 24500
12154 Kejriwal New Delhi 10000 25500
12553 Narendra Patna 10000 25250
假设,如果将一个值插入此表或使用基本工资更新为12000,则该表应如下所示更新基本工资和净工资:
EMPLOYEE TABLE
ID NAME LOCATION BASIC_SALARY NET_SALARY
的 _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ __ _ _
12102 John Bangalore 12000 30540
12155 Rana Hyderabad 12000 29400
12154 Kejriwal New Delhi 12000 30600
12553 Narendra Patna 12000 30300
12455 Sachin Mumbai 12000 30500
注意:需要使用PL / SQL中的触发器在Oracle DB上执行整个过程。
我面临的主要问题是如何在处理一条记录时使用触发器更改以前的记录值?' - 因为'触发器一次处理一行' (根据我迄今为止关于触发器的知识)
到目前为止,我已经厌倦了执行此操作的代码如下。
CREATE TABLE EMPLOYEE_PAY(
ID INT NOT NULL,
NAME VARCHAR(20),
LOCATION CHAR(25),
BASIC_SALARY DECIMAL(18,2),
NET_SALARY DECIMAL(18,2),
PRIMARY KEY(ID)
);
CREATE OR REPLACE TRIGGER EMPLOYEE_BASIC_PAY
BEFORE INSERT ON EMPLOYEE_PAY
FOR EACH ROW
BEGIN
UPDATE EMPLOYEE_PAY
SET BASIC_SALARY = :NEW.BASIC_SALARY
WHERE BASIC_SALARY != :NEW.BASIC_SALARY;
EXCEPTION
WHEN OTHERS THEN NULL;
END;
CREATE OR REPLACE TRIGGER EMPLOYEE_NET_PAY
BEFORE UPDATE OF BASIC_SALARY ON EMPLOYEE_PAY
FOR EACH ROW
BEGIN
UPDATE EMPLOYEE_PAY
SET NET_SALARY = :NEW.BASIC_SALARY * (:OLD.NET_SALARY/:OLD.BASIC_SALARY)
WHERE BASIC_SALARY != :NEW.BASIC_SALARY;
EXCEPTION
WHEN OTHERS THEN NULL;
END;
当我尝试这个时,在结果集中,基本工资仅针对INSERT INTO
更新,并且净工资保持不变。请尽快帮我解决可能的解决方案。
谢谢
答案 0 :(得分:1)
首先:您的数据模型并不好,因为您当然会注意到自己。如果所有员工的基本工资相同,为什么每个员工多余存储?如果净工资是基本工资乘以一个因素,为什么存储结果而不是因子?如果您刚刚更改了数据模型,那么根本就没有问题。
如果你必须坚持你的模特,这是我对你的触发器的评论:
CREATE OR REPLACE TRIGGER EMPLOYEE_PAY_CORRECTION AFTER INSERT OR UPDATE OF BASIC_SALARY ON EMPLOYEE_PAY FOR EACH ROW BEGIN UPDATE EMPLOYEE_PAY SET BASIC_SALARY = :NEW.BASIC_SALARY, NET_SALARY = NET_SALARY * :NEW.BASIC_SALARY / BASIC_SALARY WHERE BASIC_SALARY != :NEW.BASIC_SALARY; EXCEPTION WHEN OTHERS THEN NULL; END;