Mic*_*hel 16 sql t-sql sql-server timezone datetime
我想在tsql中循环一段时间,并打印utc datetimes和我们的本地变体.我们住在UTC +1,所以我可以轻松添加1小时,但在夏季我们生活在UTC +2.
在C#中,我可以创建一个日期时间并使用一种方法来请求UTC变体,反之亦然.
直到现在我有这个:
declare @counter int
declare @localdate datetime
declare @utcdate datetime
set @counter = 0
while @counter < 100
begin
set @counter = @counter + 1
print 'The counter is ' + cast(@counter as char)
set @utcdate = DATEADD(day,@counter,GETUTCDATE())
--set @localdate = ????
print @localdate
print @utcdate
end
Run Code Online (Sandbox Code Playgroud)
小智 23
我已经等了5年才找到更优雅的解决方案,但由于还没有出现,我会发布到目前为止我一直在使用的内容......
CREATE FUNCTION [dbo].[UDTToLocalTime](@UDT AS DATETIME)
RETURNS DATETIME
AS
BEGIN
--====================================================
--Set the Timezone Offset (NOT During DST [Daylight Saving Time])
--====================================================
DECLARE @Offset AS SMALLINT
SET @Offset = -5
--====================================================
--Figure out the Offset Datetime
--====================================================
DECLARE @LocalDate AS DATETIME
SET @LocalDate = DATEADD(hh, @Offset, @UDT)
--====================================================
--Figure out the DST Offset for the UDT Datetime
--====================================================
DECLARE @DaylightSavingOffset AS SMALLINT
DECLARE @Year as SMALLINT
DECLARE @DSTStartDate AS DATETIME
DECLARE @DSTEndDate AS DATETIME
--Get Year
SET @Year = YEAR(@LocalDate)
--Get First Possible DST StartDay
IF (@Year > 2006) SET @DSTStartDate = CAST(@Year AS CHAR(4)) + '-03-08 02:00:00'
ELSE SET @DSTStartDate = CAST(@Year AS CHAR(4)) + '-04-01 02:00:00'
--Get DST StartDate
WHILE (DATENAME(dw, @DSTStartDate) <> 'sunday') SET @DSTStartDate = DATEADD(day, 1,@DSTStartDate)
--Get First Possible DST EndDate
IF (@Year > 2006) SET @DSTEndDate = CAST(@Year AS CHAR(4)) + '-11-01 02:00:00'
ELSE SET @DSTEndDate = CAST(@Year AS CHAR(4)) + '-10-25 02:00:00'
--Get DST EndDate
WHILE (DATENAME(dw, @DSTEndDate) <> 'sunday') SET @DSTEndDate = DATEADD(day,1,@DSTEndDate)
--Get DaylightSavingOffset
SET @DaylightSavingOffset = CASE WHEN @LocalDate BETWEEN @DSTStartDate AND @DSTEndDate THEN 1 ELSE 0 END
--====================================================
--Finally add the DST Offset
--====================================================
RETURN DATEADD(hh, @DaylightSavingOffset, @LocalDate)
END
GO
Run Code Online (Sandbox Code Playgroud)
笔记:
这适用于观察夏令时的北美服务器.请将变量@Offest更改为运行SQL函数的服务器的时区偏移量(同时不观察夏令时)...
--====================================================
--Set the Timezone Offset (NOT During DST [Daylight Saving Time])
--====================================================
DECLARE @Offset AS SMALLINT
SET @Offset = -5
Run Code Online (Sandbox Code Playgroud)
随着DST规则的变化,在这里更新它们......
--Get First Possible DST StartDay
IF (@Year > 2006) SET @DSTStartDate = CAST(@Year AS CHAR(4)) + '-03-08 02:00:00'
ELSE SET @DSTStartDate = CAST(@Year AS CHAR(4)) + '-04-01 02:00:00'
--Get DST StartDate
WHILE (DATENAME(dw, @DSTStartDate) <> 'sunday') SET @DSTStartDate = DATEADD(day, 1,@DSTStartDate)
--Get First Possible DST EndDate
IF (@Year > 2006) SET @DSTEndDate = CAST(@Year AS CHAR(4)) + '-11-01 02:00:00'
ELSE SET @DSTEndDate = CAST(@Year AS CHAR(4)) + '-10-25 02:00:00'
--Get DST EndDate
WHILE (DATENAME(dw, @DSTEndDate) <> 'sunday') SET @DSTEndDate = DATEADD(day,1,@DSTEndDate)
Run Code Online (Sandbox Code Playgroud)
干杯,
假设您正在使用SQL 2005,您可以开发SQL CLR函数以获取UTC日期并转换为本地日期.
此链接是MSDN操作方法,解释如何在C#中创建标量UDF.
创建一个SQL函数
[SqlFunction()]
public static SqlDateTime ConvertUtcToLocal(SqlDateTime utcDate)
{
// over to you to convert SqlDateTime to DateTime, specify Kind
// as UTC, convert to local time, and convert back to SqlDateTime
}
Run Code Online (Sandbox Code Playgroud)
您的上述样本将成为
set @localdate = dbo.ConvertUtcToLocal(@utcdate)
Run Code Online (Sandbox Code Playgroud)
SQL CLR在部署方面有其开销,但我觉得这样的情况最适合它.
归档时间: |
|
查看次数: |
40071 次 |
最近记录: |