SQL Server-按确切的日期+时间检查给定的日期+时间是否在两个日期时间变量之间

SQL Server-按确切的日期+时间检查给定的日期+时间是否在两个日期时间变量之间,sql,sql-server,datetime,Sql,Sql Server,Datetime,我在DB表中有两个datetime列:@Start和@End 两列都包含日期和时间,例如: @Start: 2018-10-01 19:00:00 @End: 2018-10-10 23:59:00 考虑到日期和时间,我想知道当前日期是否正好在两个日期时间之间 因此,2018-10-08 16:37和2018-10-10 23:59:00将匹配此范围 2018-10-11 00:00:00不会。 在本例中,此日期比结束日期晚一分钟,因此它不在我的日期时间范围内 SELECT Id FROM T

我在DB表中有两个datetime列:@Start和@End

两列都包含日期和时间,例如:

@Start: 2018-10-01 19:00:00
@End: 2018-10-10 23:59:00
考虑到日期和时间,我想知道当前日期是否正好在两个日期时间之间

因此,2018-10-08 16:37和2018-10-10 23:59:00将匹配此范围 2018-10-11 00:00:00不会。 在本例中,此日期比结束日期晚一分钟,因此它不在我的日期时间范围内

SELECT Id FROM Table1 WHERE GETDATE() BETWEEN Start AND End
我在实际代码中不使用GETDATE,而是使用参数。问题是当前日期参数可能包含秒和毫秒,如23:59:59.123。我的代码将该日期视为不符合给定范围。但我不在乎s/ms

有解决办法吗

更新:
我想达到的精度是几分钟。所以我甚至不需要考虑秒数和毫秒数。我将使用的日期-时间格式是“yyyy-MM-dd-hh-MM”,但我不知道如何使用BETWEEN子句将开始和结束转换为显示的格式,以便比较日期。

从表1中选择Id,其中GETDATE介于“2018-10-01 19:00:00”和“2018-10-10 23:59:00”之间。

尝试

SELECT Id FROM Table1 WHERE 
         CONVERT(varchar(16),GETDATE(),121) BETWEEN 
                  CONVERT(varchar(16),[Start], 121) 
                  AND 
                  CONVERT(varchar(16),[END],121);
无字符串舍入示例

DECLARE @GetDateMinutes as datetime2;

DECLARE @X as datetime2 = getdate();

--round to minutes, could be made into a function
SET @GetDateMinutes = dateadd(minute,datepart(minute,@x),dateadd(hour, datepart(hour,@x),cast(CAST(@x as date) as datetime2)))

select @x, @GetDateMinutes

使用该技术截断秒数以避免所有字符串转换,然后只进行比较。下面是一个完整的示例,它使用交叉应用和值来封装开始和结束的截断逻辑:

-- truncate minutes from current date time
declare @currentDateTime datetime2(0) = DateAdd(minute, DateDiff(minute, 0, Convert(datetime2(0), N'2018-10-01 23:58:32.912')), 0);

select @currentDateTime as CurrentDateTime
     , a.*
from (values -- create a table of dummy values
    (Convert(datetime2(3), N'2018-10-01 19:48:14.735'), Convert(datetime2(3), N'2018-10-10 02:00:00.000'))
  , (Convert(datetime2(3), N'2018-10-01 22:43:19.532'), Convert(datetime2(3), N'2018-11-01 12:17:26.663'))
) as a (StartDateTime, EndDateTime)
cross apply (values(
    -- truncate minutes from start date time
    DateAdd(minute, DateDiff(minute, 0, Convert(datetime2(0), a.StartDateTime)), 0)
    -- truncate minutes from end date time
  , DateAdd(minute, DateDiff(minute, 0, Convert(datetime2(0), a.EndDateTime)), 0)
)) as b (StartDateTimeWithoutSeconds, EndDateTimeWithoutSeconds)
where @currentDateTime between b.StartDateTimeWithoutSeconds and b.EndDateTimeWithoutSeconds;
您的数据似乎已经从开始到结束截断了s/ms,但我想我会对所有涉及的值应用相同的逻辑,以保持一致。以下是在没有示例中所有噪声的情况下剥离s/ms的公式:

DateAdd(minute, DateDiff(minute, 0, Convert(datetime2(0), <SomeDateTime>)), 0)

你似乎想要这样的逻辑:

WHERE GETDATE() >= Start
  AND GETDATE() < DATEADD(minute, 1, End)

假设End的时间部分是23:59:00,它涵盖23:59:00和23:59:59.999…999之间的所有可能值。

您的代码应该在任何版本的SQL Server中都能工作。如果getdate正好是2018-10-10 23:59:00,直到最后一毫秒,会发生什么情况?在查询中-getdate始终返回当前日期时间。但是为了从表中获取记录,使用表列not GetDate.Between是非常糟糕的,尤其是在日期时间检查方面。下面是关于这个话题的精彩讨论@只要你的问题是完美的。唯一可能的问题是,当变量的数据类型为datetime时,您尝试推送毫秒值,如00:00:00.001或00:00:00.002。这些值被四舍五入,最后得到00:00:00.000或00:00:00.003。稍微解释一下为什么这样做会更好。@Radostina Zaykova这将使用字符串值。我有两列,所以在使用BETWEEN子句的情况下,查询看起来是这样的,它没有显示我的问题的确切解决方案:从表1中选择Id,其中getdatebetween Start和EndI接受了您的建议,它工作了!非常感谢你!而且,中间的解决方案似乎终究也能起作用。似乎是一个复杂但完整的解决方案。我将测试它并给出答案。谢谢你似乎是一个可能的解决办法。我将测试它并给出答案。非常感谢。