我需要为某些日期获得周数。例如,对于2016年1月,它应该是这样的:
[Week Number]
53 <--- for dates from Jan 1 to Jan 2
1 <--- for dates from Jan 3 to Jan 9
2 <--- for dates from Jan 10 to Jan 16
... <--- etc.
如你所见,周应从星期日开始。我使用了以下函数来设置开始日期:
SET DATEFIRST 7
这个得到周数:
DATEPART(ISOWK, SOME_DATE)
但我注意到DATEFIRST
在使用ISOWK
时不会影响结果 - 周总是从星期一开始。
那么,我做错了什么?谢谢!
UPD:
我做了一个功能,看起来效果很好:
CREATE FUNCTION [dbo].[GetWeekNumber]
(
@date as DATETIME,
@offset as INT
)
RETURNS NVARCHAR(100)
BEGIN
DECLARE @weekNumber as int
DECLARE @year as int
SET @date = DATEADD(MINUTE, @offset, @date)
SET @year = DATEPART(year, DATEADD(DAY, 1 - DATEPART(WEEKDAY, @date), CAST(@date AS DATE)))
IF @@DATEFIRST = 7
BEGIN
SET @date = DATEADD(day, 1, @date)
END
SET @weekNumber = DATEPART(ISO_WEEK, @date)
RETURN concat(@year, ', Week ', right('0' + convert(nvarchar, @weekNumber), 2))
END
您需要传递日期和时区偏移量(以分钟为单位)。并且在执行此功能之前SET DATEFIRST @startDay
(1 - 星期一,7 - 星期日)。例如:
DECLARE @date as DATETIME
SET @date = '2016-01-03 12:00'
SET DATEFIRST 1
SELECT dbo.GetWeekNumber(@date, 0) -- 2015, Week 53
SET DATEFIRST 7
SELECT dbo.GetWeekNumber(@date, 0) -- 2016, Week 01
答案 0 :(得分:4)
这是设计的。根据{{3}}:
ISO 8601包括ISO周日期系统,一个编号系统 周。每周与周四发生的年份相关联。 例如,2004年第1周(2004W01)从2003年12月29日星期一开始 到2004年1月4日星期日。
所以ISOWK
始终基于星期四,不受DATEFIRST
的影响。
要获得所需的结果,只需使用WEEK
代替ISOWK
。
更新:同样来自MSDN:
任何一年的1月1日定义了本周的起始编号 datepart,例如:DATEPART(wk,'Jan 1,xxxx')= 1,其中xxxx是 任何一年。
让第1周成为1月3日至9日的唯一方法是使用数学。从DATEPART(wk...)
值中减去1,如果结果为0,则将其设为53(或者在您的日期使用DATEADD
减去一周)。没有更简单的方法,因为按设计,任何一年的第一周都将是包含1月1日的一周。