create or replace procedure pro_update_miniwage(p_o_result out varchar2) is
/******************************************************************************
author : zhanglu
name : pro_update_miniwage
purpose : %comments%
revisions or comments 更新最低工资
ver date author description
--------- ---------- --------------- ------------------------------------
1.0 2018-4-02 zhanglu 1. created this package.
******************************************************************************/
v_step varchar2(10 char) := '0';
v_proc_name varchar2(100 char) := 'pro_update_miniwage';
v_table_name varchar2(30 char) := '';
v_reviewdate varchar2(100 char);
v_success varchar2(10 char) := util.success;
v_failed varchar2(10 char) := util.failed;
v_end_time varchar2(100 char);
v_start_time varchar2(100 char);
MAX_ROWS NUMBER DEFAULT 5000;
ROW_ID_TABLE DBMS_SQL.UROWID_TABLE;
CURSOR C1 IS
select /*+ parallel(t1,8) */ rowid from contract_info ;
-------------------------------------------------------
begin
/*init*/
v_step := '1';
v_proc_name := 'pro_update_miniwage';
v_table_name := 'contract_info';
p_o_result := v_success;
v_start_time := to_char(systimestamp, 'YYYY-MM-DD HH24:MI:SS.FF');
v_reviewdate := to_char(sysdate, 'yyyymmdd');
-- v_step := '2';
--清除当前表数据
/* execute immediate 'delete from ' || v_table_name ||
' where REVIEWDATE = ' || v_reviewdate;
commit; */
--更新个人合同表
v_step := '2';
OPEN C1;
LOOP
EXIT WHEN C1%NOTFOUND;
FETCH C1 BULK COLLECT
INTO ROW_ID_TABLE LIMIT MAX_ROWS;
FORALL I IN 1 .. ROW_ID_TABLE.COUNT
update set t.WAGES =tp.wage
WHERE ROWID = ROW_ID_TABLE(I)
COMMIT;
END LOOP;
CLOSE C1;
/*处理结束,记录日志信息*/
v_step := '3';
v_end_time := to_char(systimestamp, 'yyyy-mm-dd hh24:mi:ss.ff');
etl.write_trace(v_proc_name, v_start_time, v_end_time, p_o_result);
exception
when others then
p_o_result := v_failed;
etl.write_log(v_proc_name,
v_step,
'error ocurr:' || sqlerrm,
p_o_result);
end pro_update_miniwage;
楼上是一种游标循环的写法就是不用for in的写法,此时是需要打开游标,并且关闭游标的。以上是一种批量改更新的操作
/*+ parallel(t1,8) */ :在处理很大的任务,需要小时来计算的任务,例如大数据查询等,就可以用oracle并行技术。
优点:将一个很大的查询分成多个线程来执行,把执行的结果集中到一起,就是查询的最后结果
缺点:启用并行查询需要保证系统有足够的cpu资源等。
rowid:数据表的每一条数据都会对应一个rowid,rowid是用来描述数据所在表的物理位置。表的每一行的存储地址。rowid指向的对象是不唯一的。
create or replace procedure pro_update_miniwage(p_o_result out varchar2) is
/******************************************************************************
author : zhanglu
name : pro_update_miniwage
purpose : %comments%
revisions or comments 更新最低工资
ver date author description
--------- ---------- --------------- ------------------------------------
1.0 2018-4-02 zhanglu 1. created this package.
******************************************************************************/
v_step varchar2(10 char) := '0';
v_proc_name varchar2(100 char) := 'pro_update_miniwage';
v_table_name varchar2(30 char) := '';
v_reviewdate varchar2(100 char);
v_success varchar2(10 char) := util.success;
v_failed varchar2(10 char) := util.failed;
v_end_time varchar2(100 char);
v_start_time varchar2(100 char);
cursor emp_cursor is
select t.CONTRACTNUM,t.wages, t.AEC007,w.SALARY,w.WAGE
from contract_info t,unit_base_info u,WAGE_LEVEL w
where t.unitcode = u.unitcode and t.status='1' and w.CODE_VALUE=substr(u.areacode,0,6);
-------------------------------------------------------
begin
/*init*/
v_step := '1';
v_proc_name := 'pro_update_miniwage';
v_table_name := 'contract_info';
p_o_result := v_success;
v_start_time := to_char(systimestamp, 'YYYY-MM-DD HH24:MI:SS.FF');
v_reviewdate := to_char(sysdate, 'yyyymmdd');
-- v_step := '2';
--清除当前表数据
/* execute immediate 'delete from ' || v_table_name ||
' where REVIEWDATE = ' || v_reviewdate;
commit; */
--更新个人合同表
v_step := '2';
for rec_contract_info in emp_cursor loop
begin
--1.更新合同
IF rec_contract_info.AEC007='1' then
update contract_info r set r.WAGES =rec_contract_info.salary
WHERE rec_contract_info.SALARY>r.wages and r.contractnum=rec_contract_info.CONTRACTNUM;
elsif rec_contract_info.AEC007='2' then
update contract_info r set r.WAGES =rec_contract_info.wage
WHERE rec_contract_info.wage>r.wages and r.contractnum=rec_contract_info.CONTRACTNUM;
end if;
commit;
end;
end loop;
/*处理结束,记录日志信息*/
v_step := '3';
v_end_time := to_char(systimestamp, 'yyyy-mm-dd hh24:mi:ss.ff');
etl.write_trace(v_proc_name, v_start_time, v_end_time, p_o_result);
exception
when others then
p_o_result := v_failed;
etl.write_log(v_proc_name,
v_step,
'error ocurr:' || sqlerrm,
p_o_result);
end pro_update_miniwage;
上面这个就是用的for in来进行循环,一个一个的进行更新,循环结束后,游标自动关闭