The question: Write a PL/SQL block that gives raises to each employee according to the following criteria: Save as q3.sql no test script required. • Employees that make less than 1000 get a 6 percent raise • Employees that make between 1000 and 3000 inclusive get an 8 percent raise • Employees that make greater than 3000 get a 12 percent raise With each raise, use dbms_output to print the message ", you just got an n percent raise and your new salary is ". When all raises are completed, rollback the transaction and print the message, "He, he, he...just kidding!"
It does the correct calculations and returns no errors although it's doing the calculations on the previous record and then skipping the next.
SET SERVEROUTPUT ON
DECLARE
CURSOR sal_cursor IS
SELECT ename, sal
FROM EMP
FOR UPDATE OF sal NOWAIT;
V_sal emp.sal%TYPE;
V_ENAME EMP.Ename%TYPE;
BEGIN
FOR emp_record IN sal_cursor
LOOP
FETCH sal_cursor INTO V_Ename, V_Sal;
IF (V_SAL <= 1000) THEN
UPDATE emp
SET EMP.sal = (emp_record.sal * 1.06)
WHERE CURRENT OF sal_cursor;
v_sal := v_sal * 1.06;
ELSIF V_SAL > 1000 AND V_sal <= 3000 THEN
UPDATE emp
SET EMP.sal = (emp_record.sal * 1.08)
WHERE CURRENT OF sal_cursor;
v_sal := v_sal * 1.08;
ELSE
UPDATE emp
SET EMP.sal = (emp_record.sal * 1.12)
WHERE CURRENT OF sal_cursor;
v_sal := v_sal * 1.12;
END IF;
DBMS_OUTPUT.PUT_LINE(V_ENAME || ', you just got an n percent raise
and your new salary is ' || v_sal);
END LOOP;
DBMS_OUTPUT.PUT_LINE('He, he, he... just kidding!');
ROLLBACK;
END;
The FOR statement already fetches the record from the cursor. So don't execute FETCH in the following line.
You are mixing up two ways of handling cursors - explicit and implicit CURSOR FOR
loops. You can compare the examples linked from that syntax page.
The FOR emp_record IN sal_cursor
method automatically fetches each row into the emp_record
variable. Your explicit FETCH
then reads the next record. (I'm slightly surprised it doesn't complain about it).
SET SERVEROUTPUT ON
DECLARE
CURSOR sal_cursor IS
SELECT ename, sal
FROM EMP
FOR UPDATE OF sal NOWAIT;
V_sal emp.sal%TYPE;
BEGIN
FOR emp_record IN sal_cursor
LOOP
IF (emp_record.sal <= 1000) THEN
v_sal := emp_record.sal * 1.06;
ELSIF emp_record.sal > 1000 AND emp_record.sal <= 3000 THEN
v_sal := emp_record.sal * 1.08;
ELSE
v_sal := emp_record.sal * 1.12;
END IF;
UPDATE emp
SET EMP.sal = v_sal
WHERE CURRENT OF sal_cursor;
DBMS_OUTPUT.PUT_LINE(emp_record.ename || ', you just got an n percent raise
and your new salary is ' || v_sal);
END LOOP;
DBMS_OUTPUT.PUT_LINE('He, he, he... just kidding!');
ROLLBACK;
END;
You could also use a CASE
statement to assign the new value; or use the three separate UPDATE
statements and the RETURNING
clause to populate v_sal
, but don't know if you've learned about those yet.
If you are going to ROLLBACK
within the PL/SQL block, you should probably have an exception handler and rollback if an error is encountered as well.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.