Sql Server能否生成唯一的13位数字
我需要生成一个唯一的13位数字 如果我创建一个以13位数字作为主键的表,Sql Server是否可以以某种方式为我生成此数字 更新 我希望这个数字看起来像一个随机数,而不是一个自动递增的数字 它必须是13位数字,不应该是自动递增的,而且应该是唯一的。数字中不应该有很多零,但可以包含0-9之间的数字Sql Server能否生成唯一的13位数字,sql,sql-server,Sql,Sql Server,我需要生成一个唯一的13位数字 如果我创建一个以13位数字作为主键的表,Sql Server是否可以以某种方式为我生成此数字 更新 我希望这个数字看起来像一个随机数,而不是一个自动递增的数字 它必须是13位数字,不应该是自动递增的,而且应该是唯一的。数字中不应该有很多零,但可以包含0-9之间的数字 此号码应该看起来像信用卡号码,因此没有尾随的零。只需创建一个Guid(选择newid())&解析它。。。删除{和“-”并在其上选择长度为13的选项。我的建议是在表上有一个自动递增的标识列。然后,根据此
此号码应该看起来像信用卡号码,因此没有尾随的零。只需创建一个Guid(选择newid())&解析它。。。删除{和“-”并在其上选择长度为13的选项。我的建议是在表上有一个自动递增的标识列。然后,根据此定义值。简单的方法是:
create table t (
tId int identity(1, 1) not null,
. . .
myId cast(rand(tId)*10000000000000 as varchar(13))
)
这将它显示为计算列。当然,您可以在创建每一行时指定值。这并不保证会产生不同的结果,但您很可能会看到冲突
以下是一个替代方案,也不保证,但可能有效:
create table t (
tId varchar(13) default cast(cast(rand(checksum(getdate())*10000000000000 as bigint) as varchar(13)
. . .
)
use [chamomile];
go
if object_id(N'[utility].[table_01]', N'U') is not null
drop table [utility].[table_01];
go
if object_id(N'[utility].[generate_random_sequence]', N'FN') is not null
drop function [utility].[generate_random_sequence];
go
/*
select [utility].[generate_random_sequence] (rand());
*/
create function [utility].[generate_random_sequence] (
@random [float])
returns [bigint]
as
begin
declare @return [bigint] = ceiling(@random * 9999999999999);
while @return > 9999999999999
or @return < 1000000000000
set @return = ceiling(@random * 9999999999999);
return @return;
end;
go
if object_id(N'[utility].[table_01]', N'U') is not null
drop table [utility].[table_01];
go
create table [utility].[table_01] (
[my_id] as [utility].[generate_random_sequence] (rand())
, [flower] [sysname]
);
go
insert into [utility].[table_01]
([flower])
values (N'rose');
select *
from [utility].[table_01];
编辑:
碰撞的可能性比我预期的要高一点——我对13位散列码的直觉是,我猜,不是它应该是什么
在任何情况下,都有两个冲突源。第一个是产生相同值的随机数生成器。要处理这个问题,只需假设随机数生成器与checksum()结合使用
实际上是随机的。所以,问题是:两个小于100000000000的随机数具有相同值的可能性有多大?我会让感兴趣的人在网上搜索一个公式来计算这个值
如果生成1000个数字,则任意两个数字相同的概率基本为0%。也就是说,如果假设前1000个数字是不同的,则前1000个数字是安全的。以下是总结:
1,000 0.0000%
10,000 0.0005%
100,000 0.0500%
1,000,000 4.8771%
10,000,000 99.3262%
数十万的数值,你可能是相当安全的。当你进入百万——即使是低百万——碰撞的机会大大增加
在某种程度上,如果你想要很多很多唯一的值,你必须创建一个包含唯一值的表,以及一个选择不在表中的值的过程
正如约翰·巴萨(John Barça)所指出的:不要对Facebook上的cat照片使用此方法。我使用类似的方法在报告系统中生成随机/唯一的表名。这可能会对您有所帮助。只需调整乘数以影响最终的整数长度
SELECT CONVERT(BIGINT,RAND()*10000000000000)
作为一张桌子
CREATE TABLE #test (testID INT,
UniqueID AS CONVERT(BIGINT,RAND()*10000000000000))
INSERT INTO #test (testID)
SELECT 1
SELECT * FROM #TEST
DROP TABLE #test
只要在testID中插入一个值(每次可以是1),就会生成一个新的UniqueID。不过,在任何生产表上都应该有一个主键
注意:虽然重复发生的几率很小,但仍然有可能发生。类似的事情可能会发生:
create table t (
tId varchar(13) default cast(cast(rand(checksum(getdate())*10000000000000 as bigint) as varchar(13)
. . .
)
SELECT CEILING(RAND()*9999999999999)
use [chamomile];
go
if object_id(N'[utility].[table_01]', N'U') is not null
drop table [utility].[table_01];
go
if object_id(N'[utility].[generate_random_sequence]', N'FN') is not null
drop function [utility].[generate_random_sequence];
go
/*
select [utility].[generate_random_sequence] (rand());
*/
create function [utility].[generate_random_sequence] (
@random [float])
returns [bigint]
as
begin
declare @return [bigint] = ceiling(@random * 9999999999999);
while @return > 9999999999999
or @return < 1000000000000
set @return = ceiling(@random * 9999999999999);
return @return;
end;
go
if object_id(N'[utility].[table_01]', N'U') is not null
drop table [utility].[table_01];
go
create table [utility].[table_01] (
[my_id] as [utility].[generate_random_sequence] (rand())
, [flower] [sysname]
);
go
insert into [utility].[table_01]
([flower])
values (N'rose');
select *
from [utility].[table_01];
使用[洋甘菊];
去
如果对象_id(N'[utility].[table_01]',N'U')不为null
删除表[utility]。[table_01];
去
如果对象_id(N'[utility].[generate_random_sequence]',N'FN')不为空
删除函数[实用工具][生成随机序列];
去
/*
选择[utility]。[generate_random_sequence](rand());
*/
创建函数[实用工具]。[生成随机序列](
@随机[浮动])
返回[bigint]
作为
开始
声明@return[bigint]=上限(@random*999999999);
而@return>999999999
或@return<10000000000
设置@return=上限(@random*999999999);
return@return;
结束;
去
如果对象_id(N'[utility].[table_01]',N'U')不为null
删除表[utility]。[table_01];
去
创建表[utility]。[table_01](
[my_id]为[utility]。[generate_random_sequence](rand())
,[flower][sysname]
);
去
插入[实用工具].[表_01]
([花])
价值观(N'rose');
选择*
来自[实用工具][表_01];
为什么特别指定一个13位数字?它必须只有13位还是最多13位?以1000000000开头的标识列如何?您想要一个函数来创建ID,还是想要一个自动递增的ID,它总是13位数字?请您更好地解释一下:@YanireRomero更新了我的问题,希望它能澄清问题。42算13位数字吗?它和0000000000042一样吗?多少是“太多”零?Guid不是所有的数字。你测试过吗?因为我执行了1000次,它生成了1000个13位数字。是的。如果不将数字存储在表中并进行比较来实现它,就无法“保证”它始终是唯一的。例如,如果rand返回0.00001,你会返回多少位数字希望答案能四舍五入到最接近的整数?啊!我想我会取-1。我认为天花板()做了它所做的事,但我错了兰德()的意思生成。顺便说一句,-1不是我写的。冲突的变化取决于表的大小。只有9*10^13个13位数的数字。如果这是Facebook上猫咪照片的唯一ID,你将在几周内用完:-)@JohnBarça…我编辑了答案。我无法得到上传到Faceb的猫咪照片数量的好答案我确实找到了每天300000000张照片的参考资料。如果我们假设其中0.1%可以归类为“猫照”(对某些人来说,这似乎是一个极低的估计),那么你是对的。一个重复的13位猫照片代码可能会在两到三周内出现。这本质上是生日问题——人们通常低估了碰撞的可能性。猫和狗为极端工程所做的令人惊讶的事情。由于大量不相关的HTML标记,我们无法编辑此帖子。P请以明文形式键入SQL。