序列是oracle用来生产一组等间隔的数值。序列是递增,而且连续的。oracle主键没有自增类型,所以一般使用序列产生的值作为某张表的主键,实现主键自增。序列的编号不是在插入记录的时候自动生成的,必须调用序列的方法来生成(一般调用nextval方法)。我们也可以编写表的insert触发器来进自动生成。
  创建语法:

create sequence 序列名称
[start with 初始量] 
[increment by 递增量] 
[maxvalue 最大值| nomaxvalue] 
[minvalue 最小值| nominvalue] 
[cycle | nocycle] 
[cache 缓存个数| nocache];

start with:生成第一个序列号,对于升序列,其默认值为序列最小值;对于降序序列,其默认值为序列的最大值 。
increment by:用于指定序列号之间的间隔,其默认值为1,如果integer为正值,则生成的序列按升序排列,如果integer为负值,则生成的序列将按降序排列。
maxvalue:序列可以生成的最大值。
nomaxvalue:oracle将升序序列的最大值设为1027,将降序序列的最大值设为-1.这是默认选项。
minvalue:minvalue必须小于或等于start with的值,并且必须小于maxvalue的值。
nominvalue:oracle将升序的最小值设为1,或将降序序列的最小值设为-1026.这是默认值。
cycle:序列在达到最大值或最小值后,将继续从头开始生成值。
nocycle:序列在达到最大值或最小值后,将不能再继续生成值。不写默认为nocycle这是默认选项 。
cache:预先分配一组序列号,并将其保留在内存中,这样可以更快地访问序列号.当用完缓存中的所有序列号.oracle将生成另一组数值,并将其保留在缓存中。
nocache:不会加快访问速度而预先分配序列号,如果在创建序列时忽略了cache和nocache,orcale将默认缓存20个序列号。

修改语法:
alter sequence 序列名称
[start with 初始量] 
[increment by 递增量] 
[maxvalue 最大值| nomaxvalue] 
[minvalue 最小值| nominvalue] 
[cycle | nocycle] 
[cache 缓存个数| nocache];

二、例子

   以下代码person表如下:

重置mysql 自增索引重新计数_最小值

DROP TABLE person ;
CREATE TABLE person (
id NUMBER(11) NOT NULL ,
username VARCHAR2(255 ) NULL ,
age NUMBER(11) NULL ,
password VARCHAR2(255) NULL ,
PRIMARY KEY (id)
)

重置mysql 自增索引重新计数_最小值

  创建序列

create sequence seq_tb_person
minvalue 1
maxvalue 999999999999999999999999999
start with 1
increment by 1
cache 20;

  使用序列

insert into person (id, username, age, password) values (seq_tb_person.nextval, '张三', 20, 'zhang123')

 

修改序列

alter sequence seq_tb_person
minvalue 1
maxvalue 999999999999999999999999999
-- start with 49 对于已经启动的序列,无法设置初始值
increment by 1
cache 20;

  查看用户的序列:

select sequence_name, min_value, max_value, increment_by, last_number from user_sequences;

  删除序列

drop sequence 序列名;

  通过USER_OBJECTS可以查看用户拥有的序列,USER_SEQUENCES可以查看序列的设置。

 

重置序列

oracle序列创建以后,如果想重置序列从 0 开始,逐渐递增1,可以采用如下存储过程:

重置mysql 自增索引重新计数_最小值

1 create or replace
 2 procedure reset_seq( p_seq_name in varchar2 )
 3 is
 4     l_val number;
 5 begin
 6     execute immediate
 7     'select ' || p_seq_name || '.nextval from dual' INTO l_val;
 8 
 9     execute immediate
10     'alter sequence ' || p_seq_name || ' increment by -' || l_val || 
11                                                           ' minvalue 0';
12 
13     execute immediate
14     'select ' || p_seq_name || '.nextval from dual' INTO l_val;
15 
16     execute immediate
17     'alter sequence ' || p_seq_name || ' increment by 1 minvalue 0';
18 end;

重置mysql 自增索引重新计数_最小值

存储过程创建以后,调用该存储过程,参数是要重置的序列名称:

call reset_seq(‘test_seq’);

使用下面的SQL语句查询需要重置的序列:

重置mysql 自增索引重新计数_最小值

1 SELECT  a.sequence_name 序列名称,
 2 a.min_value 序列最小值,
 3 to_char(to_number( a.max_value)) 序列最大值,
 4 a.last_number 序列当前值,
 5 CASE  a.last_number WHEN 1 THEN '--不需要重置;' ELSE 
 6 'CALL seq_reset(''' || a.sequence_name || ''');' END 重置序列脚本,
 7 'DROP SEQUENCE ' || a.sequence_name 删除序列脚本,
 8 'RENAME ' || a.sequence_name || ' TO {newname}'  重命名脚本
 9 FROM USER_SEQUENCES a WHERE a.last_number<>1
10 ORDER BY a.sequence_name ASC;

重置mysql 自增索引重新计数_最小值

重置序列脚本这列查询出来的值就是调用存储过程重置序列的SQL语句,直接执行SQL将重置序列。

 

三、注意点

  • 一个序列可以被多张别使用,不过一般建议为每个表建立单独的序列。
  • 当使用到序列的事务发生回滚。会造成序列号不连续。在用生成的序列值作为编号做插入数据库操作时,可能遇到事务提交失败,从而导致序号不连续。
  • 大量语句发生请求,申请序列时,为了避免序列在运用层实现序列而引起的性能瓶颈。Oracle序列允许将序列提前生成 n个先存入内存,在发生大量申请序列语句时,可直接到运行最快的内存中去得到序列。但cache个数最好不要设置过大,因为在数据库重启时,会清空内存信息,预存在内存中的序列会丢失,当数据库再次启动后,序列从上次内存中最大的序列号+1 开始存入n个。这种情况也能会在数据库关闭时也会导致序号不连续。