设为首页收藏本站

EPS数据狗论坛

 找回密码
 立即注册

QQ登录

只需一步,快速开始

查看: 1712|回复: 0

SQL Server 序列(SEQUENCE)使用

[复制链接]

36

主题

375

金钱

563

积分

初级用户

发表于 2019-6-24 16:04:44 | 显示全部楼层 |阅读模式

众所周知,在之前的SQL SERVER版本中,一般采用GUID或者IDENTITY来作为标示符,但是IDENTITY是一个表对象,只能保证在一张表里面的序列,当我们遇到以下情况时,
1.png
如上表,我们需要在多表之间,实现ID的一致性,在SQL SERVER里面就会有一定的麻烦,通常我们会使用额外使用一张TEMP表来映射这些ID的关系然后再从中取序列来完成。

SEQUENCE在ORACLE中其实很早就存在了,SQL SERVER 2012的SEQUENCE功能和那个相似,是一个基于SCHEMA的对象,所以可以被多表调用。

序列是用户定义的绑定到架构的对象,该对象可根据创建序列所依据的规范来生成数值序列。 这组数值以定义的间隔按升序或降序生成,并且可配置为用尽时重新启动(循环)。 序列不与特定表相关联,这一点与标识列不同。 应用程序将引用某一序列对象以便检索其下一个值。 序列与表之间的关系由应用程序控制。 用户应用程序可以引用一个序列对象,并跨多个行和表协调值。与在插入行时生成的标识列值不同,应用程序可以获得下一个序列号,而不必通过调用 NEXT VALUE FOR 函数来插入行。 使用 sp_sequence_get_range 同时获取多个序列号。

SEQUENCE语法如下: (创建一个序列对象并指定其属性)
  1. CREATE SEQUENCE [schema_name . ] sequence_name  
  2.     [ AS [ built_in_integer_type | user-defined_integer_type ] ]  
  3.     [ START WITH <constant> ]  
  4.     [ INCREMENT BY <constant> ]  
  5.     [ { MINVALUE [ <constant> ] } | { NO MINVALUE } ]  
  6.     [ { MAXVALUE [ <constant> ] } | { NO MAXVALUE } ]  
  7.     [ CYCLE | { NO CYCLE } ]  
  8.     [ { CACHE [ <constant> ] } | { NO CACHE } ]  
  9.     [ ; ]
复制代码


sequence_name 指定数据库中标识序列的唯一名称。 类型为 sysname。
[ built_in_integer_type | user-defined_integer_type 序列可定义为任何整数类型。如果未提供任何数据类型,则默认 bigint类型。
START WITH 序列对象返回的第一个值。 START 值必须小于或等于序列对象的最大值并大于或等于其最小值。
INCREMENT BY 每次调用 NEXT VALUE FOR 函数时序列对象值递增(如果为负数,则为递减)的值。
MIN和MAX 分别设置最小和最大值
CYCLE 设置是否循环,默认循环选项是 NO CYCLE
CACHE 通过最大限度地减少生成序列编号所需的磁盘 IO 数,可以提高使用序列对象的应用程序的性能。 默认值为 CACHE。

ORACLE中有SEQUENCE的功能,SQL SERVER类似的功能使用IDENTITY列实现,但是有很大的局限性。在2012中,微软终于增加了 SEQUENCE 对象,功能和性能都有了很大的提高。
我们可以在SSMS中创建也可以使用SQL SERVER脚本创建序列对象:
2.jpg
3.jpg
使用SQL创建序列对象:
  1. IF EXISTS(SELECT * FROM sys.sequences WHERE name = N'TestSeq')
  2.     DROP SEQUENCE TestSeq;
  3. GO
  4. --创建序列对象
  5. CREATE SEQUENCE TestSeq AS TINYINT
  6.     START WITH 1
  7.     INCREMENT BY 1;
  8. GO
  9. --创建表
  10. CREATE TABLE TEST(ID tinyint,  Name varchar(150))
  11. --产生序列号码并插入表中
  12. INSERT INTO TEST(ID,Name) VALUES(NEXT VALUE FOR TestSeq, 'allen')
  13. INSERT INTO TEST(ID,Name) VALUES(NEXT VALUE FOR TestSeq, 'kevin')

  14. SELECT * FROM TEST
复制代码

4.png
  1. --产生序列可以重复使用,下面的例子当序列号码超过255后又重新从0开始。
  2. CREATE SEQUENCE [dbo].[Test1Seq] AS [tinyint]
  3.   START WITH 0
  4.   INCREMENT BY 5
  5.   CYCLE

  6. SELECT NEXT VALUE FOR [Test1Seq]
复制代码

5.png
  1. --重新将序列初始值变为5
  2. ALTER SEQUENCE dbo.TestSeq RESTART WITH 5;

  3. SELECT * FROM sys.sequences WHERE name = 'TestSeq'
复制代码

6.png
  1. --共享序列,两个表可以使用同一个序列对象(IDENTITY列是不可以的)
  2. CREATE SEQUENCE dbo.Seq AS INT
  3.    START WITH 1
  4.    INCREMENT BY 1

  5. CREATE TABLE dbo.Examp1
  6. (
  7.    Seq INT NOT NULL,
  8.    Name VARCHAR(50) NOT NULL
  9. );

  10. CREATE TABLE dbo.Examp2
  11. (
  12.    Seq INT NOT NULL,
  13.    Name VARCHAR(50)NOTNULL
  14. );
  15.   
  16. INSERT INTO dbo.Examp1(Seq,Name) VALUES (NEXT VALUE FOR dbo.Seq, 'Tom');
  17. INSERT INTO dbo.Examp2(Seq,Name) VALUES (NEXT VALUE FOR dbo.Seq, 'Jerry');

  18. SELECT * FROM Examp1
  19. SELECT * FROM Examp2
复制代码

7.png
  1. --可以直接在查询中使用序列对象(IDENTITY列是不可以的)
  2. CREATE SEQUENCE SeqOrder AS tinyint
  3.     START WITH1
  4.     INCREMENT BY1
  5.     MINVALUE 1
  6.     NO MAXVALUE
  7.     CYCLE;
  8. GO

  9. SELECT ID, Name,NEXT VALUE FOR SeqOrder OVER(ORDER BY Name DESC) AS [Order] FROM test;
复制代码

8.png
为了提升性能,还可以使用CACHE选项,这样就可以将序列号码缓存到内存,减少IO操作,值得一提的是序列对象可以指定最大值和最小值,增加值可以为负数。
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

关闭

站长推荐上一条 /1 下一条

客服中心
关闭
在线时间:
周一~周五
8:30-17:30
QQ群:
653541906
联系电话:
010-85786021-8017
在线咨询
客服中心

意见反馈|网站地图|手机版|小黑屋|EPS数据狗论坛 ( 京ICP备09019565号-3 )   

Powered by BFIT! X3.4

© 2008-2028 BFIT Inc.

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