|
先说什么是uuid。全局唯一标识符 (GUID)。很多时候,并行的n个系统,要给某类产生某个编号。但是n个系统之间不能够重复,这样的编号,就要使用uuid。大家都到ms的站点去下载过东西吧,看这个链接(http://www.microsoft.com/downloads/details.aspx?FamilyID=262d25e3-f589-4842-8157-034d1e7cf3a3&displaylang=zh-cn)中(262d25e3-f589-4842-8157-034d1e7cf3a3)就是一个例子。在.net fcl中,有一个类专门负责这档子事,那就是System.Guid类。
在数据库中,oracle和ms均已经有了实现。在oracle中,like this:
SQL> select sys_guid() from dual;
SYS_GUID()
--------------------------------
E5BCF4C6635AB664E03073CA38A91E02
SQL> /
SYS_GUID()
--------------------------------
E5BCF4C6635BB664E03073CA38A91E02
SQL>
这里(http://www.adp-gmbh.ch/ora/sql/sys_guid.html)有sys_guid的说明。
在我的系统中,连续的两个guid是连续的。这是非常偶然的。虽然他们是连续的,但是,绝对是不重复。我听高手说,这个以来于操作系统对guid的实现。
在oracle中,通过给某一个列(应该是char(36)或者是varchar(36)这样的类型)指定默认值为SYS_GUID(),就实现了我们需要的效果。
再来看sql-server。在sql-serer中,有一个数据类型叫做uniqueidentifier,我们把数据类型指定为这个,系统自动为这个列填充默认值newid()。来看newid的效果吧:
1> select newid();
2> select newid();
3> go
------------------------------------
76413BFB-B088-419B-BB73-912F3318D75F
(1 行受到影响)
------------------------------------
78CEED8C-799B-4266-A5AE-3BE83F01AF93
(1 行受到影响)
1>
pg8都出来了,似乎没有uudi的类型。
laserhe他们做了一个pguuid的包,给你的pg打上这个包以后,据说,就有uuid这个类型。但是,这样的做法不具备通用性;不见得每个系统,你都可以登陆上去给人家打个包。我还听laserhe说,pg全球开发组,并不打算添加guid函数。因为他们认为双字节的随机数,也是同样的效果。
或者是为了兼容,或者是为了数据移植方便,非常有必要弄一个uuid生成工具。uuid,基本上都是mac+当前时间。ok,知道了这些,来看看我的系统上是怎么实现的:
先创建一个语言plgsql,你在执行shell命令就可以了,因为这样,可以省去一大堆参数。在shell提示符下键入
createlang -d <你的数据库名字> plpgsql
我们之所以创建这语言,是为了后面写函数的时候方便些。(标准sql会使我们的函数麻烦n多。)
现在我们来创建一个uudi函数吧。
在sql提示符下,键入:
CREATE OR REPLACE FUNCTION new_uuid()
RETURNS text AS
'
declare
vWork1 text;
vWork2 text;
vMac text;
begin
-- replace vMac with the mac of your own box
vMac=\'00:0D:56:FD:A0:DB\';
vWork1 := md5(vMAC || now());
vWork2 := SUBSTRING(vWork1, 1, ||\'-\'|| SUBSTRING(vWork1,9,4) ||\'-\'|| SUBSTRING(vWork1,13,4) ||\'-\'|| SUBSTRING(vWork1,17,4) ||\'-\'|| SUBSTRING(vWork1,21,12);
RETURN cast(vWork2 as varchar(36));
end;
'
LANGUAGE 'plpgsql' VOLATILE;
请注意,用你自己的mac替换我上面写的mac地址。ok,我们的uuid函数,就ok了。看看效果吧:
lacl=# SELECT new_uuid();
new_uuid
--------------------------------------
ac206895-90bd-2e0e-f5fa-8fb76327a1dc
(1 DD)
lacl=# SELECT new_uuid();
new_uuid
--------------------------------------
6f376ae9-9284-52b0-92d1-3db731b64a1c
(1 DD)
lacl=#
ok,我们的sql-server风格的uuid就完成了。你在你的表里面指定某个列的某人值为new_uudi函数就可以了。比如我的一个例子:
CREATE TABLE announcement
(
announcement_id "char"(36) DEFAULT new_uuid(),
)
。
完。 |
|