2014-10-17 140 views
1

我需要生成唯一的标识符,它必须不再是5的长度,因为它的数字不适合,有没有办法在oracle数据库中生成唯一的字符串?如何生成oracle字符串序列?

+0

您需要能够表示多少个值?使用一个正常的序列,但存储十六进制等价物将使您从100,000个值到1,048,756,但这可能仍然太低?使用26个字符将得到11,881,376个可能的值;包括数字会给60,466,176。但更复杂的是,转换一个序列。 – 2014-10-17 11:35:51

+0

为什么限制在5? (架构改变会让imo更有意义)。另外,即使你坚持5限制,你需要多少个独特的值?可能最好更改架构并使用数字或sys_guid。 – tbone 2014-10-17 13:26:51

+0

5上的lemetation是因为来自客户端的准备休息API的文档,我需要超过10亿个对象。 – 2014-10-17 17:01:45

回答

0

这可能帮助: http://www.deep-data-mining.com/2012/06/five-ways-of-creating-unique-record.html

该位看起来有用:

据Oracle文档,SYS_GUID生成并返回一个全局唯一标识符(原糖值),由16个字节。

例如,我们的Oracle系统上,我可以这样做:

select sys_guid() uniq_id from dual; 

而得到这样的:

059D828192804EABE05400144FFB6CA7 

下一次我:

059D828192A34EABE05400144FFB6CA7 

一些数字每次递增。

我可以限制到5个字符,其中包括每次运行时改变字符串的位:

select substr(sys_guid(),9,5) uniq_id from dual; 

为了得到例如

92D14 
+3

正如我所看到的,您只是剪切了生成的字符串,并且它可能不是唯一的。 – 2014-10-17 11:27:16

+0

是的,对不起,我想我的回答可能是一堆旧垃圾: - \抱歉。我认为这个号码是独一无二的,但也许它不会是我不确定的。对不起浪费时间。 – 2014-10-17 11:36:04

2

您可以尝试使用基地36:http://en.wikipedia.org/wiki/Base_36

SQL:Base 36 to Base 10 conversion using SQL only

由于评论这个答案,我加入一个例子:

该函数将基地10号码到由字母组成的基地。

create or replace 
function basen(n10 in number, letters in varchar2) return varchar2 as 
    s  varchar2(1000); 
    len  number := length(letters); 
    base10 number := n10; 
begin 
    if len <= 0 then 
    return null; 
    end if; 

    loop 
    if base10 < len then 
     return substr(letters, base10+1, 1) || s; 
    end if; 
    s := substr(letters, mod(base10, len)+1,1) || s; 
    base10 := floor(base10/len); 
    end loop; 

    return s; 
end baseN; 

这个函数转换从base10到base36:

create or replace function base36(n10 in number) return varchar2 as 
begin 
    return basen(n10, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'); 
end base36; 

用户可以创建一个共同序列与适当的MINVALUE和MAXVALUE和在触发使用的方法之一的上方,SQL等

2

此方法使用HEX格式的数字。

select to_char(seq.nextval, 'fm0XXXX') 
    from dual; 

或者这更紧凑的方法使用的所有符号的ASCII码33和122之间:

select num, 
     chr(33 + mod(floor(num/(90*90*90*90)), 90))|| 
     chr(33 + mod(floor(num/(90*90*90)), 90))|| 
     chr(33 + mod(floor(num/(90*90)),90))|| 
     chr(33 + mod(floor(num/90),90))|| 
     chr(33 + mod(num,90)) as x00000 
from (select seq.nextval as num 
     from dual); 

基本上,这是基于90号的表示。