Oracle表关联更新几种方法

打印 上一主题 下一主题

主题 226|帖子 226|积分 678

1、测试表及数据准备

  1. create table T_update01(ID int ,infoname varchar2(32),sys_guid varchar2(36));
  2. create table T_update02(ID int ,infoname varchar2(32),sys_guid varchar2(36));
  3. insert into T_update01
  4. select 1,N'1_updateName',sys_guid() from dual
  5. union
  6. select 2,N'2_updateName',sys_guid() from dual;
  7. commit;
  8. insert into T_update02
  9. select 1,N'update_set_exists',sys_guid() from dual;
  10. insert into T_update02
  11. select 2,N'update_set_cursor',sys_guid() from dual;
  12. insert into T_update02
  13. select 3,N'3_Name',sys_guid() from dual;
  14. commit;
  15. -- 查询表T_update01、T_update02
  16. select * from T_update01;
  17.         ID INFONAME                       SYS_GUID
  18. ---------- ------------------------------ ------------------------------------
  19.          1 1_updateName                   189F5A1099BF6606E0639C0AA8C0F15E
  20.          2 2_updateName                   189F5A1099C06606E0639C0AA8C0F15E
  21. select * from T_update02;
  22.         ID INFONAME                       SYS_GUID
  23. ---------- ------------------------------ ------------------------------------
  24.          1 update_set_exists              189F5A1099C46606E0639C0AA8C0F15E
  25.          2 update_set_cursor              189F5A1099C56606E0639C0AA8C0F15E
  26.          3 3_Name                         189F5A1099C66606E0639C0AA8C0F15E
复制代码
2、update set column ... where exists


2.1、update set 单列字段

  1. -- update set 单列字段,更新满足关联条件的所有数据
  2. update T_update01 T1
  3. set infoname=(select T2.infoname from T_update02 T2 where T2.ID=T1.ID)
  4. where exists (select 1 from T_update02 T2 where T2.ID=T1.ID );
  5. -- update set 单列字段 ,更新满足特定条件ID=1的数据
  6. update T_update01 T1
  7. set infoname=(select T2.infoname from T_update02 T2 where T2.ID=T1.ID)
  8. where T1.ID=1;
  9. -- 本次执行更新满足特定条件T_update01表的ID=1
  10. SCOTT@prod02> select * from T_update01;
  11.         ID INFONAME                       SYS_GUID
  12. ---------- ------------------------------ ------------------------------------
  13.          1 update_set_exists              189F5A1099BF6606E0639C0AA8C0F15E
  14.          2 2_updateName                   189F5A1099C06606E0639C0AA8C0F15E
复制代码
2.2、update set 多列字段

  1. -- T_update01表多插入一行数据
  2. insert into T_update01
  3. select 3,N'insert03',sys_guid() from dual;
  4. commit;
  5. select * from T_update01;
  6.         ID INFONAME                       SYS_GUID
  7. ---------- ------------------------------ ------------------------------------
  8.          1 update_set_exists              189F5A1099BF6606E0639C0AA8C0F15E
  9.          2 2_updateName                   189F5A1099C06606E0639C0AA8C0F15E
  10.          3 insert03                       189F5A1099C76606E0639C0AA8C0F15E
  11. update T_update01 T1
  12. set (sys_guid,infoname) = (select T2.sys_guid,T2.infoname from T_update02 T2 where T2.ID=T1.ID)
  13. where exists (select 1 from T_update02 T2 where T2.ID=T1.ID );
  14. commit;
  15. -- 更新后检查,sys_guid,infoname两列的值和T_update02一样了
  16. select * from T_update01;
  17.         ID INFONAME                       SYS_GUID
  18. ---------- ------------------------------ ------------------------------------
  19.          1 update_set_exists              189F5A1099C46606E0639C0AA8C0F15E
  20.          2 update_set_cursor              189F5A1099C56606E0639C0AA8C0F15E
  21.          3 3_Name                         189F5A1099C66606E0639C0AA8C0F15E
  22. select * from T_update02;
  23.         ID INFONAME                       SYS_GUID
  24. ---------- ------------------------------ ------------------------------------
  25.          1 update_set_exists              189F5A1099C46606E0639C0AA8C0F15E
  26.          2 update_set_cursor              189F5A1099C56606E0639C0AA8C0F15E
  27.          3 3_Name                         189F5A1099C66606E0639C0AA8C0F15E
复制代码
3、利用游标

  1. -- T_update02数据更新一下,方便使用游标更新的结果显示
  2. update T_update02 set INFONAME='cursor is select' where id>=2;
  3. commit;
  4. select * from T_update02;
  5.         ID INFONAME                       SYS_GUID
  6. ---------- ------------------------------ ------------------------------------
  7.          1 update_set_exists              189F5A1099C46606E0639C0AA8C0F15E
  8.          2 cursor is select               189F5A1099C56606E0639C0AA8C0F15E
  9.          3 cursor is select               189F5A1099C66606E0639C0AA8C0F15E
  10. -- 使用用游标更新T_update01的INFONAME字段,使其和T_update02 where id>=2
  11. declare
  12.   cursor cur_my_source is select infoname,id from T_update02;
  13.   begin
  14.      for cur_my_target in cur_my_source loop
  15.        update T_update01 set infoname=cur_my_target.infoname where id=cur_my_target.id;
  16.      end loop;
  17.          commit;
  18. end;
  19. /
  20. -- 检查查询结果
  21. select * from T_update01;
  22.         ID INFONAME                       SYS_GUID
  23. ---------- ------------------------------ ------------------------------------
  24.          1 update_set_exists              189F5A1099C46606E0639C0AA8C0F15E
  25.          2 cursor is select               189F5A1099C56606E0639C0AA8C0F15E
  26.          3 cursor is select               189F5A1099C66606E0639C0AA8C0F15E
复制代码
4、merge into子句

  1. create table T_merg01(ID int ,infoname varchar2(32),sys_guid varchar2(36));
  2. create table T_merg02(ID int ,infoname varchar2(32),sys_guid varchar2(36));
  3. insert into T_merg01
  4. select 1,N'1_Name',sys_guid() from dual
  5. union
  6. select 2,N'2_Name',sys_guid() from dual;
  7. commit;
  8. select * from T_merg01;
  9.         ID INFONAME                       SYS_GUID
  10. ---------- ------------------------------ ------------------------------------
  11.          1 1_Name                         189F5A1099BB6606E0639C0AA8C0F15E
  12.          2 2_Name                         189F5A1099BC6606E0639C0AA8C0F15E
  13. insert into T_merg02
  14. select 1,N'merge_into_Name1',sys_guid() from dual;
  15. insert into T_merg02
  16. select 3,N'3_Name',sys_guid() from dual;
  17. select * from T_merg02;
  18.         ID INFONAME                       SYS_GUID
  19. ---------- ------------------------------ ------------------------------------
  20.          1 merge_into_Name1               189F5A1099BD6606E0639C0AA8C0F15E
  21.          3 3_Name                         189F5A1099BE6606E0639C0AA8C0F15E
  22. merge into T_merg01 T1
  23. using T_merg02 T2 on (T1.id=T2.id)
  24. when matched then update set infoname=T2.infoname
  25. when not matched then insert (ID,infoname,sys_guid) values(T2.ID ,T2.infoname,T2.sys_guid);
  26. commit;
  27. select * from T_merg01;
  28.         ID INFONAME                       SYS_GUID
  29. ---------- ------------------------------ ------------------------------------
  30.          1 merge_into_Name1               189F5A1099BB6606E0639C0AA8C0F15E
  31.          2 2_Name                         189F5A1099BC6606E0639C0AA8C0F15E
  32.          3 3_Name                         189F5A1099BE6606E0639C0AA8C0F15E
  33. -- 可以发现T_merg01表的ID=1的INFONAME=merge_into_Name1和T_merg02表ID=1的值一样了
  34. -- 可以发现T_merg01表多了一行数据是T_merg02表ID=3的这一行数据
复制代码
5、Oracle 23c/AI 新特性

不论是已发版本Oracle23c free照旧最终发布的长期支持的Oracle23Ai,表关联更新update和删除delete语句易用且更加优雅,雷同SQLServer的关联更新
以下操作基于的情况
SQL*Plus: Release 23.0.0.0.0 - Developer-Release on Fri May 17 11:17:54 2024
Version 23.2.0.0.0

5.1、关联更新update


  1. TESTUSER@FREEPDB1> create table t_emp as select EMPLOYEE_ID,DEPARTMENT_ID,SALARY from employees;
  2. Table created.
  3. TESTUSER@FREEPDB1> desc t_emp;
  4. Name                                      Null?    Type
  5. ----------------------------------------- -------- ----------------------------
  6. EMPLOYEE_ID                                        NUMBER(6)
  7. DEPARTMENT_ID                                      NUMBER(4)
  8. SALARY                                             NUMBER(8,2)
  9. TESTUSER@FREEPDB1> select * from t_emp where DEPARTMENT_ID=110;
  10. EMPLOYEE_ID DEPARTMENT_ID     SALARY
  11. ----------- ------------- ----------
  12.         205           110      12008
  13.         206           110       8300
  14. TESTUSER@FREEPDB1> update t_emp set DEPARTMENT_ID=null,SALARY=null where DEPARTMENT_ID=110;
  15. 2 rows updated.
  16. TESTUSER@FREEPDB1> commit;
  17. Commit complete.
  18. TESTUSER@FREEPDB1> select * from t_emp where DEPARTMENT_ID is null;
  19. EMPLOYEE_ID DEPARTMENT_ID     SALARY
  20. ----------- ------------- ----------
  21.         178                     7000
  22.         205
  23.         206
  24. -- oracle 23c SQL增强 表关联更新        
  25. TESTUSER@FREEPDB1> update t_emp t1 set t1.DEPARTMENT_ID=t2.DEPARTMENT_ID,t1.SALARY=t2.SALARY from employees t2 where t2.EMPLOYEE_ID=t1.EMPLOYEE_ID and t1.DEPARTMENT_ID is null;
  26. 3 row updated.
  27. TESTUSER@FREEPDB1> commit;
  28. Commit complete.
  29. TESTUSER@FREEPDB1> select t1.* from t_emp t1 where t1.DEPARTMENT_ID=110;
  30. EMPLOYEE_ID DEPARTMENT_ID     SALARY
  31. ----------- ------------- ----------
  32.         205           110      12008
  33.         206           110       8300
复制代码
5.2、关联删除delete

  1. TESTUSER@FREEPDB1> delete t_emp t1 from employees t2 where t2.EMPLOYEE_ID=t1.EMPLOYEE_ID and t2.DEPARTMENT_ID=110;
  2. 45 rows deleted.
  3. TESTUSER@FREEPDB1> commit;
  4. Commit complete.
  5. TESTUSER@FREEPDB1> select t1.* from t_emp t1 where t1.DEPARTMENT_ID=110;
  6. no rows selected
复制代码


免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。
回复

使用道具 举报

0 个回复

倒序浏览

快速回复

您需要登录后才可以回帖 登录 or 立即注册

本版积分规则

诗林

高级会员
这个人很懒什么都没写!

标签云

快速回复 返回顶部 返回列表