1

我的数据库中有一个名为Tasks. 该表中的每条记录都有 2 个字段:StartDateEndDate
我需要创建递归存储过程,它将在这些日期的中间发送邮件。
例如:
开始是2013-10-22 12:00:00:000
结束是2013-10-24 12:00:00:000

我可以:

SELECT DATEADD(ms, 
       DATEDIFF(ms,'2013-10-22 12:00:00:000', '2013-10-24 12:00:00:000')/2,
       '2013-10-22 12:00:00:000')

然后检查现在是否大于那个日期,如果是,那么我可以发送邮件。

但我需要递归地这样做:第一个主必须在中间发送,第二个在 1/4 中,第三个在 1/8 等,最后在剩下 2 小时时发送。

我的第一个想法是在我的表中添加列并在其中存储最后一个主要的日期,但我想避免修改表。

我认为递归选择会更好,但欢迎任何关于如何解决的想法:)

编辑:我的示例小提琴:http ://sqlfiddle.com/#!3/25d0d/1

我的例子:
任务开始于 2013-10-22 8:00,结束于 2013-10-22 21:00

程序从 2013 年 10 月 22 日 10:00 开始,
第一条记录的发送时间是 14:30,所以没有什么要发送的

程序从 2013 年 10 月 22 日 12:00 开始,
第一条记录的发送时间是 14:30,所以什么都没有发送

程序从 2013 年 10 月 22 日 14:00 开始,
第一条记录的发送时间是 14:30,所以什么都没有发送

程序从 2013 年 10 月 22 日 16:00 开始,
第一条记录的发送时间为 14:30,因此发送有关该任务的邮件

下一条消息应该在 17:45 左右发送

程序从 2013 年 10 月 22 日 18:00 开始,

第一条记录的发送时间为 17:45,因此发送有关该任务的邮件

下一条消息应该在 19:22 左右发送

程序从 2013 年 10 月 22 日 20:00 开始,
第一条记录的发送时间是 19:22,所以应该发送邮件,
但是因为从 19:22 到 21:00 少于 2 小时,所以不需要邮件

4

1 回答 1

1

无法在 SQL Server 2005 上进行测试,但在 SQL Server 2008 上,您可以使用递归公用表表达式(用您的过程参数替换下面的固定日期)。第一部分获取第一次,第二部分不断计算最后一次和结束时间之间的时间,直到时间差小于4小时;

WITH cte AS (
  SELECT DATEADD(ms, 
                 DATEDIFF(ms, '2013-10-22 12:00:00:000', 
                              '2013-10-24 12:00:00:000')/2,
                              '2013-10-22 12:00:00:000'
                               ) a
  UNION ALL
  SELECT DATEADD(ms, DATEDIFF(ms,cte.a, '2013-10-24 12:00:00:000')/2, cte.a)
  FROM cte
  WHERE DATEDIFF(hour, cte.a, '2013-10-24 12:00:00:000') >= 4
)
SELECT * FROM cte;

一个用于测试的 SQLfiddle

编辑:要获取邮件时间在过去 2 小时内的任务(即应该生成邮件),您可以使用类似的东西;

WITH cte AS (
  SELECT taskid,enddate, DATEADD(s, 
                  DATEDIFF(s, startdate, enddate)/2, startdate) tm
  FROM Tasks
  UNION ALL
  SELECT taskid,enddate, DATEADD(ms, DATEDIFF(ms,cte.tm, enddate)/2, cte.tm)
  FROM cte
  WHERE DATEDIFF(hour, cte.tm, enddate) >= 4
)
SELECT taskid, tm FROM cte WHERE tm < GETDATE() AND DATEDIFF(hour, tm, GETDATE()) < 2

如果作业以不规则的间隔运行,您可能希望将其截断GETDATE()为仅几个小时。

于 2013-10-22T08:49:26.407 回答