SF *_*per 2 t-sql random datetime
更新包含DATETIME
TSQL列的表的最简单方法是什么,RANDOM
值为2个日期?
我看到与之相关的各种帖子,但是当你ORDER BY DATE
在更新之后,他们的Random值实际上是连续的.
Iai*_*der 10
首先假设您有一个数据库,其中包含一个包含start datetime列和end datetime列的表,它们共同定义了一个datetime范围:
CREATE DATABASE StackOverflow11387226;
GO
USE StackOverflow11387226;
GO
CREATE TABLE DateTimeRanges (
StartDateTime DATETIME NOT NULL,
EndDateTime DATETIME NOT NULL
);
GO
ALTER TABLE DateTimeRanges
ADD CONSTRAINT CK_PositiveRange CHECK (EndDateTime > StartDateTime);
Run Code Online (Sandbox Code Playgroud)
并假设该表包含一些数据:
INSERT INTO DateTimeRanges (
StartDateTime,
EndDateTime
)
VALUES
('2012-07-09 00:30', '2012-07-09 01:30'),
('2012-01-01 00:00', '2013-01-01 00:00'),
('1988-07-25 22:30', '2012-07-09 00:30');
GO
Run Code Online (Sandbox Code Playgroud)
以下SELECT
语句返回开始日期时间,结束日期时间和伪随机日期时间,其中精度大于或等于开始日期时间且小于第二个日期时间:
SELECT
StartDateTime,
EndDateTime,
DATEADD(
MINUTE,
ABS(CHECKSUM(NEWID())) % DATEDIFF(MINUTE, StartDateTime, EndDateTime) + DATEDIFF(MINUTE, 0, StartDateTime),
0
) AS RandomDateTime
FROM DateTimeRanges;
Run Code Online (Sandbox Code Playgroud)
因为该NEWID()
函数是非确定性的,所以每次执行都会返回不同的结果集.这是我刚刚生成的结果集:
StartDateTime EndDateTime RandomDateTime
----------------------- ----------------------- -----------------------
2012-07-09 00:30:00.000 2012-07-09 01:30:00.000 2012-07-09 00:44:00.000
2012-01-01 00:00:00.000 2013-01-01 00:00:00.000 2012-09-08 20:41:00.000
1988-07-25 22:30:00.000 2012-07-09 00:30:00.000 1996-01-05 23:48:00.000
Run Code Online (Sandbox Code Playgroud)
RandomDateTime列中的所有值都位于StartDateTime和EndDateTime列中的值之间.
这种用于生成随机值的技术归功于Jeff Moden.他在SQL Server Central上撰写了一篇关于数据生成的精彩文章.阅读它以获得更全面的解释.注册是必需的,但它是值得的.
我们的想法是从开始日期时间生成一个随机偏移量,并将偏移量添加到开始日期时间,以便在开始日期时间和结束日期时间之间获得新的日期时间.
表达式DATEDIFF(MINUTE, StartDateTime, EndDateTime)
表示开始日期时间和结束日期时间之间的总分钟数.偏移量必须小于或等于此值.
该表达式ABS(CHECKSUM(NEWID()))
为每一行生成一个独立的随机正整数.表达式可以具有0到2,147,483,647之间的任何值.这个表达式mod第一个表达式给出了一个有效的偏移量,以分
epxression DATEDIFF(MINUTE, 0, StartDateTime)
表示开始日期时间和参考日期时间之间的总分钟数0
,这是简写的时间'1900-01-01 00:00:00.000'
.引用日期时间的值无关紧要,但重要的是在整个表达式中使用相同的引用日期.将其添加到偏移量以获取参考日期时间之间的总分钟数.
ecapsulating DATEADD函数通过将前一个表达式生成的分钟数添加到引用日期时间,将其转换为日期时间值.
你可以使用RAND
这个:
select cast(cast(RAND()*100000 as int) as datetime)
Run Code Online (Sandbox Code Playgroud)
从这里开始
Sql-Fiddle看起来很不错:http://sqlfiddle.com/#!3/b9e44/2/0