本次的业务需求是:在一张旧表t_bnet_customer上增加了一个新的字段,这个字段在值在另一张表t_customer_extend里面,一一对应来更新;
原先的语句:
UPDATE t_bnet_customer a
SET a.customer_id = (SELECT b.cust_nbr FROM t_customer_extend b
WHERE a.id = b.bnet_id )
WHERE EXISTS (SELECT b.cust_nbr FROM t_customer_extend b
WHERE a.id = b.bnet_id)
后来的语句:
update (
select a.customer_id a1, b.cust_nbr b1
from t_bnet_customer a,
t_customer_extend b
where a.id = b.bnet_id
) set a1 = b1 ;
上面的语句被oracle限制了,不能执行的话,换成下面的:
update (
select /*+ BYPASS_UJVC */ a.customer_id a1, b.cust_nbr b1
from t_bnet_customer a,
t_customer_extend b
where a.id = b.bnet_id
) set a1 = b1 ;
---------------------------------原因如下---------------------------------
http://lastcaress.blog.sohu.com/149585028.html
用implicit view update的时候,如果源表没加唯一性约束,会碰到
ORA-01779: cannot modify a column which maps to a non key-preserved table
比如用下面的pzl_test_1 b的col2去更新pzl_test a的col2,用两表的col1关联
SQL> select col1,col2 from pzl_test;
COL1 COL2
--------------------------------------------------------------------------------
1 A
2 B
3 C
SQL> select col1,col2 from pzl_test_1 b;
COL1 COL2
--------------------------------------------------------------------------------
2 BB
3 CC
4 DD
如果b表的col1字段没有唯一约束,执行
SQL> update
2 (select a.col2 col2a,b.col2 col2b
3 from pzl_test a,
4 pzl_test_1 b
5 where a.col1=b.col1
6 )
7 set col2a=col2b;
结果是:
ERROR at line 7:
ORA-01779: cannot modify a column which maps to a non key-preserved table
然后给b表加上唯一性约束:
SQL> create unique index idx_pzl_test_1 on pzl_test_1(col1);
Index created.
再执行之前的update语句,就可以成功了
SQL> 省略..
2 rows updated.
查看a表结果:
SQL> select col1,col2 from pzl_test;
COL1 COL2
--------------------------------------------------------------------------------
1 A
2 BB
3 CC
显示正常。
先rollback了它。
SQL> rollback;
Rollback complete.
ORACLE要求b表关联字段唯一是合理的,否则更新a表时,如果b表有多条记录对应,不知道用哪条记录去更新才好。
但在实际开发时,经常会碰到虽然逻辑上能保证b表的关联字段唯一,但不想,或者无法给它加唯一性约束的情况(它是唯一,却不能给它一个名分。。)
以前碰到这样的情况,我是用update a + 两句子查询或者先过滤b表再merge来实现的。但这样对b表的访问次数是implicit view update的2倍,降低了效率。(
10g以上版本可以用一句merge实现和view update相同的效果,但我们最大的两个数据库都是9i)
昨天晚上逛街时发现,原来有个hint可以强制oracle跳过唯一检查,在b表没有建唯一约束的情况下也能够用implicit view update
这就是/*+BYPASS_UJVC*/
把b表的唯一索引干掉:
SQL> drop index idx_pzl_test_1;
Index dropped.
再执行前面的update语句(加上hint):
SQL> update
2 (select /*+BYPASS_UJVC*/ a.col2 col2a,b.col2 col2b
3 from pzl_test a,
4 pzl_test_1 b
5 where a.col1=b.col1
6 )
7 set col2a=col2b;
2 rows updated.
更新成功了。更新后结果和建了唯一约束完全一样。
也就是说,只要能在逻辑上保证b表的关联字段唯一,就不是非得给它一个名分了。
借用一句格调低下的广告语:如果不能给它一个名分,就送它一套BYPASS_UJVC吧!
如果b表里关联字段不唯一,会产生什么效果呢?
下面测试一下:
往b表里插一条记录
SQL> insert into pzl_test_1 values('2','BBB');
1 row created.
现在b表里col1='2'的有2条了:'BB'和'BBB'。
执行update:
SQL> update
2 (select /*+BYPASS_UJVC*/ a.col2 col2a,b.col2 col2b
3 from pzl_test a,
4 pzl_test_1 b
5 where a.col1=b.col1
6 )
7 set col2a=col2b;
3 rows updated.
注意,这里显示是3 rows updated,虽然a表只有2条记录被更新。
查看a表,发现col1='2'的col2,会更新到b表中对应记录之一的值,究竟对应到哪条现在还不太清楚,应该和b表中记录的地址、implicit view的写法有关。以后有空再研究研究。
分享到:
相关推荐
的字段如果要加二个,不能连着加.得关了程 序再开才能进行.否则弹的记事本内容中,前 面的内容还是上次的字段路径. 但可以连着加不同的字段类型. 比如加完TEXT类型的字段.不能接着加TEXT 类型的字段,但可以加DATE/...
一个shp文件中有多个要素,根据某个字段中的值,批量将值一样要素的输出为一个shp,并以该值命名新导出的shp文件。(下载后在工具箱右键添加即可)
MySQL批量对表增加指定字段,会快速实现批量字段的添加。写了2个存储存储过程,执行即可。方便快速!
可以实现在arcgis中按照矢量文件的字段值批量转成以矢量字段值命名的kmz文件,便于在奥维软件中查看
本工具是一款可以根据excel填写的参数添加字段工具,只需在excel填好参数,在arcgis导入可以全自动添加,非常快速、方便。只要是添加字段的,他都可以哦!!!
批量给SHP加字段
一个SHP文件内涉及多个要素...如某个SHP里有两个要素,要素的其中一个属性字段为“范围”,这两个要素的字段值分别问“范围1”、“范围2”,使用此工具后,能一次输出“范围1.kml”和“范围2.kml”。(arcgis10.4版本)
KETTLE实现循环批量更新表添加字段,将kettle资源库抽取到另一个数据库中并输出抽取表单,(本文用的是MySQL)
在arcgis中利用批处理对SHP批量加字段addfield
SQL Server 2008 批量修改字段类型,查询出所有需要修改的字段,然后修改
ArcGIS(ArcPy)脚本excel批量添加字段
Mybatis Plus 自定义批量插入或批量更新(根据唯一索引)
Arcgis中利用python语言对shp文件批量添加字段,注释详细,只需更改shp文件所在文件夹路径,以及相关字段名称、类型、长度等设置即可
通过python遍历某个文件下面的所有gdb文件,然后对每个gdb文件中的某个字段批量修改成某个值
arcmap——数据处理工具shp按字段批量导出dwg.tbx
以下小编给大家列出了三种实现thinkphp批量更新数据的方法,写的不好还请见谅,有意见欢迎提出,共同学习进步! 方法一: //批量修改 data二维数组 field关键字段 参考ci 批量修改函数 传参方式 function batch_...
将模板用arcmap打开(注意:要选择内容列表-按绘制顺序列出显示图层),点击此功能,系统自动读取模板的字段(字段属性包括字段名称,字段类型,字段长度,字段精度,保留小数位)存储到选择的txt文件中(自己添加也...
批量为shp添加字段,注释很清晰,还不够完善,有更好的意见欢迎及时提出,一起交流学习。批量为shp添加字段,注释很清晰,还不够完善,有更好的意见欢迎及时提出,一起交流学习。
oracle 用SQL通过使用游标实现批量更新表中某个字段的值表名和字段名需要修改,字符串的截取的方法需要根据实际情况修改
按字段属性合并导出