11gR2向表插入序列值跳值问题(deferred segment 新特性带来的糟糕体验)

我们知道序列是和当前会话有关联的,譬如:

12:20:53 OE@orcl> CREATE SEQUENCE empseq
12:21:01   2  START WITH 100
12:21:01   3  INCREMENT BY 1
12:21:01   4  ORDER NOCYCLE;

序列已创建。

已用时间:  00: 00: 00.03
12:21:01 OE@orcl>
12:21:01 OE@orcl> SELECT empseq.CURRVAL  FROM dual;
SELECT empseq.CURRVAL  FROM dual
       *
第 1 行出现错误:
ORA-08002: 序列 EMPSEQ.CURRVAL 尚未在此会话中定义


已用时间:  00: 00: 00.03
12:21:19 OE@orcl> SELECT empseq.nextval  FROM dual;

   NEXTVAL
----------
       100
第一次必须先NEXTVAL一下得到当前值

,然后在同一个会话下你再使用此序列就没问题了。

在11gR2 oracle使用了一个deferred segment新技术,也就是创建表的时候,不会立即创建,而是延时到插入值的时候才开始创建,这样带来的好处是,建表速度快,而且不占资源,但是却带来一些问题,譬如我们将要讨论的插入序列问题。

如下:

11:48:58 CRY@orcl> create sequence seq_tt;

序列已创建。

已用时间:  00: 00: 00.03
11:49:09 CRY@orcl> create table test(id number,ss varchar2(100));

表已创建。

已用时间:  00: 00: 00.01
11:49:17 CRY@orcl> select seq_tt.nextval from dual;

   NEXTVAL
----------
         1

已用时间:  00: 00: 00.00
11:49:28 CRY@orcl> insert into test values(seq_tt.nextval,'test test');

已创建 1 行。

已用时间:  00: 00: 00.04
11:49:36 CRY@orcl> select * from test;

        ID SS
---------- ------------------------------------------------------------
         3 test test


很糟糕的,序列seq_tt跳过了2,直接把3插入到了表中。

我们来取消deferred segment这个特性再来试试(注意:11gr2中此值默认为TRUE的)

alter session set deferred_segment_creation=false;(使用此语句来取消延迟段创建特性)

13:08:25 CRY@orcl> create sequence seq_tt;

序列已创建。

已用时间:  00: 00: 00.01
13:09:09 CRY@orcl> create table test(id number,ss varchar2(100));

表已创建。

已用时间:  00: 00: 00.20
13:09:12 CRY@orcl> insert into test values(seq_tt.nextval,'test test');

已创建 1 行。

已用时间:  00: 00: 00.01
13:09:19 CRY@orcl> select * from test;

        ID SS
---------- ---------------------------------------------------------------------
         1 test test


当我们取消延时创建表之后,序列插入正常了。

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值