Oracle SQL 游标增加工资直到达到最大金额

Oracle SQL Cursor to increase salaries until the max amount is reached

对于这个问题,我需要将 employees.salary 增加 20%,从最低工资开始(升序)直到用完 $100,000。我很难找到关于如何保存更新后的剩余金额直到 100,000 美元用完的解决方案。这是我到目前为止所拥有的。谢谢

declare
 cursor mancur is
   select salary from employees order by salary asc;
 tempcur     mancur%ROWTYPE;
 profits     number := 100000;
 tempsalary  employees.salary%type;
 tempinc     number(8,2);
begin
 open mancur;
 loop
   fetch mancur into tempcur;
   tempinc := tempcur.salary * 1.20;
   tempsalary := profits - tempcur.salary;
   dbms_output.put_line(tempcur.salary || ' increased by 20% ' || tempinc || ', Bonus amount left ' || tempsalary);
   exit when mancur%notfound; --when 100,000 has been used
   --update employees set salary = salary * 1.20 where employee_id = tempcur.employee_id;
 end loop;
 close mancur;
end;
/
begin
 open mancur;
  loop
   fetch mancur into tempcur;
   tempinc := tempcur.salary * 1.20;
   profits := profits - (tempinc-tempcur.salary);  -- You have to keep subtracting the increment amount to find if bonus is exhausted or not
      if profits <=0 Then  --When all your funds are exhausted
         Exit
      End if
              dbms_output.put_line(tempcur.salary || ' increased by 20% ' || tempinc || ', Bonus amount left ' || profits);
      exit when mancur%notfound; --when 100,000 has been used
   --update employees set salary = salary * 1.20 where employee_id = 
      tempcur.employee_id;
   end loop;
 close mancur;
end;
/
declare
 profits     number := 100000;
 tempinc     number(8,2);
begin
for hike_loop in (select employee_id,salary from employees order by salary asc) loop
if profits <= 0 then
break;
end if;
tempinc := hike_loop.salary * 0.20;
if (tempinc <= profits) then
update employees set salary = salary * 1.20 where employee_id = hike_loop.employee_id;
profits := profits - tempinc;
else
break;
end if;
end loop;
end;
/

只是为了好玩:这是应该如何简单地完成 SQL。这个任务不需要函数或过程,除非它是 PL/SQL class 中的作业。即使这样,相同的 MERGE 语句也应该是 PL/SQL 代码中的 运行,这样处理是在设置级别完成的,而不是逐行完成的。

这也解决了 "small remaining amount" 与目前发布的解决方案不同的问题。如果不足以将 "last" 的薪水增加 20%,则可以增加,但最多增加 100,000 美元。而如果两个或两个以上的员工工资相同"the first to be left out",则"remaining amount"平分给这些员工。

merge into employees e
  using ( select employee_id,
                 sum  (salary) over (order by salary)     as sum_salary,
                 count(salary) over (partition by salary) as cnt
          from   employees
        ) x
    on ( e.employee_id = x.employee_id )
when matched then update
  set salary = 1.2 * salary + case when sum_salary <= 100000 / 0.2 then 0
                                   else (100000 - 0.2 * sum_salary) / cnt end  
    where sum_salary - cnt * salary <= 100000 / 0.2
;