oracle生成顺序号,[原创]oracle 顺序号生成函数。仿Sequence

问题提出自项目中的老代码:一个Bill表,存储所有的表单信息,比如:员工入职单,离职单等等。(别喷,我知道要分多个表。但领导的意愿你是没办法违背的)表单的单据号是以四个字母+年月日+数字顺序号来表示。每次取新单据号时要从Bill表里(按生成规则)查询出最大的那个单据号,再拆分出来,再给顺序号加1,组合好后再写回。哈哈这就是老代码。

随着软件行业的进步,各种技巧层出不穷。而针对顺序号生成的方法也有好巨大改进。

这里其中的一篇。看过这个之后就想自己动手也写一个。于是:

顺序号表

--id序列表

create table SEQUENCES

(

id VARCHAR2(20) not NULL PRIMARY KEY,--标识

minvalue NUMBER default 1,--最小值

maxvalue NUMBER default 9999999999999999999999999999,--最大值

currentvalue NUMBER DEFAULT 1,--当前值

increaseby NUMBER default 1,--增量

CYCLE CHAR(1) default '' --是否循环

)

生成函数

--获取 select NextValue('abc') from dual;

create or replace function NextValue(arg varchar2) return number IS

PRAGMA AUTONOMOUS_TRANSACTION;

Result number;

x NUMBER;

a NUMBER;

i NUMBER;

c Char(1);

BEGIN

IF TRIM(arg) IS NULL THEN--防止值入空字符串

RAISE_Application_Error(-6502,'param "arg" is not valide.',TRUE);

END IF;

<>

SELECT COUNT(1) INTO x FROM Sequences WHERE ID = arg;

IF x = 0 THEN

BEGIN

BEGIN

INSERT INTO Sequences (ID) VALUES(arg);--防止并发同时插入相同的Id值。需要将id设为主键

EXCEPTION

WHEN OTHERS THEN

GOTO top;

END;

COMMIT;

RETURN 1;

END;

ELSE

BEGIN

SELECT s.currentvalue + s.increaseby,s.maxvalue,s.minvalue,s.cycle INTO Result,a,i,c FROM Sequences s WHERE ID = arg FOR update;--for update将锁定此行记录

IF RESULT < a THEN--未超出最大值

BEGIN

UPDATE Sequences SET currentvalue = Result WHERE ID = arg;

COMMIT;

return(Result);

END;

ELSE

BEGIN

IF c = '' THEN--不循环

BEGIN

RAISE_Application_Error(-6502,'out of range.',TRUE);

END;

ELSE

BEGIN--循环

UPDATE Sequences SET currentvalue = i WHERE ID = arg;

COMMIT;

RETURN i;

END;

END IF;

END;

END IF;

END;

END IF;

END;

是的,我使用了参数。这样就使得这个表更加有用,而非只单独处理一种类型顺序号。同时对并发进行了处理。让你只可能取得一个值,而不会出现重复的值。当然所有的result都没有进行格式化,而是直接输出。在PLSQL中进行函数test,打开两个窗口,单步调试,可以看到在insert或select for update时都会阻塞其它session对此表的操作。这样可以使用result的结果唯一。

如果将表的名称的传入,那么你可以扔掉sequence了。

oracle 顺序号生成函数。仿Sequence

问题提出自项目中的老代码:一个Bill表,存储所有的表单信息,比如:员工入职单,离职单等等.(别喷,我知道要分多个表.但领导的意愿你是没办法违背的)表单的单据号是以四个字母+年月日+数字顺序号来表示. ...

Oracle数据库中序列&lpar;SEQUENCE&rpar;的用法详解

Oracle数据库中序列(SEQUENCE)的用法详解   在Oracle数据库中,序列的用途是生成表的主键值,可以在插入语句中引用,也可以通过查询检查当前值,或使序列增至下一个值.本文我们主要介绍了 ...

&lbrack;原创&rsqb;Oracle 12c 抢先安装手迹

[前言] Oracle 12c 终于投放市场了,唉,等了很久了.据官方说这是一个为云计算平台量身定做的版本....且不管真的假的,先让我们把它装上再说. 注:笔者在安装的过程中发现12c的安装过程,较 ...

Oracle中序列(Sequence)详解

一 序列定义 序列(SEQUENCE)是序列号生成器,可以为表中的行自动生成序列号,产生一组等间隔的数值(类型为数字).不占用磁盘空间,占用内存. 其主要用途是生成表的主键值,可以在插入语句中引用,也 ...

Oracle笔记之序列&lpar;Sequence&rpar;

Oracle中序列是一种数据对象,可以视为一个等差数列,我们自增就是一个遍历这个数列的过程,可以取当前值,也可以将当前值自加n后返回,Sequence与表没有太大的关系,有的时候如果表的主键是数值类型 ...

oracle的序列号(sequence)

oracle的自增列,要采用序列号(sequence). 初始化阶段要手动建立一个sequence,然后插入的时候,还要手动自己去读这个sequence的nextval赋给相关字段,如ID,麻烦的很. ...

Oracle修改序列(Sequence)起始值问题

Oracle 序列(Sequence)主要用于生成流水号,在应用中经常会用到,特别是作为ID值,拿来做表主键使用较多. 但是,有时需要修改序列初始值(START WITH)时,有同仁使用这个语句来修改 ...

Oracle Auto Increment Column - Sequence as Default Value

Solution 1: Prior to Oracle 11g, sequence assignment to a number variable could be done through ...

Oracle中序列(SEQUENCE)的使用一例

曾经在触发器中使用序列(SEQUENCE): create or replace trigger TRI_SUPPLIER before insert on SUPPLIER for each row ...

随机推荐

转-C&num;让枚举返回字符串

下面的手段是使用给枚举项打标签的方式,来返回字符串 下面分别定义一个属性类,和一个枚举帮助类 [AttributeUsage(AttributeTargets.Field,AllowMultiple  ...

MySQL中order by中关于NULL值的排序问题

MySQL中order by 排序遇到NULL值的问题 MySQL数据库,在order by排序的时候,如果存在NULL值,那么NULL是最小的,ASC正序排序的话,NULL值是在最前面的. 如果我们 ...

使用PowerShell读、写、删除注册表键值

访问注册表键值 在PowerShell中,用户可以通过类似于HKCU:(作为HKEY_CURRENT_USER)和HKLM:(代表HKEY_LOCAL_MATCHINE)的虚拟驱动器访问注册表键值. ...

RHEL安装时加载第三方raid驱动

IBM x3650 M3服务器做完RAID之后,不能直接的安装Linux系统,会报出没有硬盘的错误 过程如下: 1.到IBM的官方网站下载device drive 下载后的为:ibm_dd_sraid ...

effective c&plus;&plus; 条款4 make sure that objects are initialized before they are used

1 c++ 类的数据成员的初始化发生在构造函数前 class InitialData { public: int data1; int data2; InitialData(int a, int b) ...

php代码常见错误详解整理

错误类型: 一.未使用二进制上传   代码:    Fatal error: This encoded file is corrupted. Please refer to http://www.ze ...

top&comma;ps查看进程使用内存情况

ps -e -o 'pid,comm,args,pcpu,vsz,stime,user,uid' |grep chrome|grep -v grepwatch 'ps -e -o 'pid,comm, ...

Easyui combobox 始终选择第一个的问题

//必须指定 id 和 text $('#contact_city').combobox({ valueField:'id', textField:'text', });

UIView使用UIMotionEffect效果

UIView使用UIMotionEffect效果 这个效果在模拟器上看不了,所以无法截图. UIView+MotionEffect.h  +  UIView+MotionEffect.m // // ...

python学习笔记——multiprocessing 多进程组件 进程池Pool

1 进程池Pool基本概述 在使用Python进行系统管理时,特别是同时操作多个文件目录或者远程控制多台主机,并行操作可以节约大量时间,如果操作的对象数目不大时,还可以直接适用Process类动态生成 ...