2014-08-29 151 views
0

我有一个DATEDIFF函数的问题。(Transact-SQL)DATEDIFF和闰年

我的日期格式是dd/mm/yyyy

@START_DATE = 01/02/2004
@END_DATE = 29/01/2014

查询(DATEDIFF(DAY,@START_DATE,@END_DATE)/365)回报10,但正确的年数为9。发生这种情况是因为我的查询不考虑闰年。


我能做些什么来保持准确的计数? 谢谢。

+1

有一年接近365.25天之间的数,所以你不要指望你的算术是正确的。 – 2014-08-29 10:51:21

回答

0

我相信下面的逻辑你想要做什么:

datediff(year, 
      @START_DATE - datepart(dayofyear, @START_DATE) + 1, 
      @END_DATE - datepart(dayofyear, @START_DATE) + 1 
      ) as d2 

注:这会将该日期作为datetime,因为算术更容易表达。你也可以写为:

datediff(year, 
      dateadd(day, - datepart(dayofyear, @START_DATE) + 1, @START_DATE), 
      dateadd(day, - datepart(dayofyear, @START_DATE) + 1, @END_DATE) 
      ) as d2 

下面的查询是一个演示:

select datediff(year, 
       startdate - datepart(dayofyear, startdate) + 1, 
       enddate - datepart(dayofyear, startdate) + 1 
       ) as d2 
from (select cast('2004-02-01' as datetime) as startdate, 
      cast('2014-01-31' as datetime) as enddate 
     union all 
     select cast('2004-02-01' as datetime) as startdate, 
      cast('2014-02-01' as datetime) as enddate 

    ) t 
+0

它的工作原理! :D但我有一个问题:为什么要添加+1? – Andryx93 2014-08-29 13:23:44

+0

@ Andryx93。 。 。 2014-01-05是今年的第五天。如果你减去5,你会得到2013-12-31。这个想法是将日期规范化为年初以进行比较。 – 2014-08-29 13:35:53

+0

非常感谢! – Andryx93 2014-08-29 13:57:34

1

您可以创建一个函数来解决:

CREATE FUNCTION [dbo].[getYears] 
(
    @START_DATE datetime, 
    @END_DATE datetime 
) 
RETURNS int 
AS 
BEGIN 
    DECLARE @yrs int 
    SET @yrs =DATEDIFF(year,@START_DATE,@END_DATE) 
    IF (@END_DATE < DATEADD(year, @yrs, @START_DATE)) 
     SET @yrs = @yrs -1 
    RETURN @yrs 
END 

还要检查this

1

技术上会有一年365.242天,占闰年,所以当:

FLOOR(DATEDIFF(day, @STARTDATE, @ENDDATE)/365.242) 

应该更正确。

测试:

SELECT FLOOR(DATEDIFF(day, '1980-01-16','2015-01-15')/365.242), 
     FLOOR(DATEDIFF(day, '1980-01-16','2015-01-16')/365.242) 

的ResultSet:

干杯!

0

计算end_date中闰日的数量在start_date中减去闰日的数量。从你的DATEDIFF中扣除答案。

DECLARE 
    @START_DATE DATETIME = '2004-02-01', 
    @END_DATE DATETIME = '2014-01-29' 

SELECT (
     DATEDIFF(DAY,@START_DATE,@END_DATE) 
      - (
       (CONVERT(INT,@END_DATE - 58)/1461) 
       - 
       (CONVERT(INT,@START_DATE - 58)/1461) 
      ) 
     )/365 

-58忽略月和1900年2月

/1461是天的闰年