我想结合日期和时间,并与utc日期进行比较

时间:2013-02-18 09:10:27

标签: asp.net sql sql-server-2008

当我写这个查询时

SELECT Convert(datetime,Convert(varchar,CAST(GETUTCDATE() AS DATE))+' '+ 
       CONVERT(varchar, cast(meas_pain.datetime AS time))) FROM meas_pain

它对我有用但是当我在WHERE子句中使用相同的部分时,它会给出错误'转换从字符串转换日期和/或时间时失败。'

SELECT schedules.id 
FROM meas_pain LEFT JOIN schedules ON schedules.id=meas_pain.schd_id 
WHERE meas_pain.schd_id=9150 AND  
      Convert(datetime,(Convert(varchar,CAST(GETUTCDATE() AS DATE))+' '+
      CONVERT(varchar, cast(meas_pain.datetime AS time)))) < 
      CONVERT(datetime,DATEADD(Minute,0,getutcdate()))

任何人都可以解释一下吗?

1 个答案:

答案 0 :(得分:2)

我不确定为什么这个错误没有出现在你的select语句中,因为我可以使用

重现错误
SET DATEFORMAT DMY;
SELECT  CONVERT(DATETIME, CONVERT(VARCHAR,CAST(GETUTCDATE() AS DATE)))

<强> Example of Error

您依赖于本地化转换设置,您应该使用显式转换,例如

SET DATEFORMAT DMY;
SELECT  CONVERT(DATETIME, CONVERT(VARCHAR, CAST(GETUTCDATE() AS DATE), 111), 111)

通过明确定义日期格式以将其转换为varchar和varchar(111),您可以避免任何隐含的转换。

然而,如果你的日期/时间是这样存储的,那么就不需要进行varchar的所有转换,这只是出错的可能性,以及不必要的工作,你可以简单地为日期时间添加一个时间。 e.g。

DECLARE @Date1 DATETIME = DATEADD(HOUR, 1, GETUTCDATE()),
        @Date2 DATETIME = DATEADD(DAY, 1, GETUTCDATE());

SELECT  [Date1] = @Date1,
        [Date2] = @Date2,
        [Date1/Time2] = CAST(CAST(@Date1 AS DATE) AS DATETIME) +
                           CAST(@Date2 AS TIME);

从我可以从您的查询中收集到的内容,您只是尝试获得meas_pain.datetime的时间小于当前UTC时间的结果,而不考虑日期。因此,您应该能够将查询简化为:

SELECT  schedules.id 
FROM    meas_pain 
        LEFT JOIN schedules 
            ON schedules.id = meas_pain.schd_id 
WHERE   meas_pain.schd_id = 9150
AND     CAST(meas_pain.[DateTime] AS TIME) < CAST(GETUTCDATE() AS TIME);

并删除进一步的冗余转换。

<强> Simplified example on SQL Fiddle

<强> ADENDUM

显然这个时间比较并不是你所追求的(虽然它是你发布的查询正在做的事情),所以我假设GETUTCDATE()仅用于演示。

您尝试执行的转换等同于:

CAST(CAST(GETUTCDATE() AS DATE) AS DATETIME) + CAST(meas_pain.[DateTime] AS TIME)

<强> Another example on SQL Fiddle using the above conversion