【问题标题】:Difference of two date time in sql serversql server中两个日期时间的差异
【发布时间】:2011-01-08 03:52:42
【问题描述】:

有什么办法可以取sql server中两个datetime的区别?

例如,我的日期是

  1. 2010-01-22 15:29:55.090
  2. 2010-01-22 15:30:09.153

所以,结果应该是14.063 seconds

【问题讨论】:

  • 你得到了所有的datediff 答案,但似乎没有一个提醒你,根据参数排序,你可能会从中得到负面结果。

标签: sql sql-server datetime


【解决方案1】:

关于 DateDiff 的一个警告,它会计算您通过指定为单位的边界的次数,因此如果您正在寻找精确的时间跨度,则会遇到问题。 例如

select datediff (m, '20100131', '20100201')

给出的答案是 1,因为它从 1 月到 2 月跨越了边界,所以即使跨度是 2 天,datediff 也会返回值 1 - 它跨越了 1 个日期边界。

select datediff(mi, '2010-01-22 15:29:55.090' , '2010-01-22 15:30:09.153')

再次给出值 1,它通过了分钟边界一次,所以即使它大约是 14 秒,当使用 Minutes 作为单位时,它也会作为一分钟返回。

【讨论】:

    【解决方案2】:
    SELECT DATEDIFF (MyUnits, '2010-01-22 15:29:55.090', '2010-01-22 15:30:09.153')
    

    根据DATEDIFF on MSDN替换“MyUnits”

    【讨论】:

      【解决方案3】:
      SELECT  DATEDIFF(day, '2010-01-22 15:29:55.090', '2010-01-22 15:30:09.153')
      

      day 替换为您想要获得差异的其他单位,例如secondminute 等。

      【讨论】:

        【解决方案4】:

        我可以提到 MS SQL Server 的四个非常有用的重要功能:

        1)函数DATEDIFF()负责计算两个日期之间的差异,结果可以是“年季月日日周时分秒毫秒微秒纳秒”,在第一个参数上指定(日期部分):

        select datediff(day,'1997-10-07','2011-09-11')
        

        2)您可以使用函数GETDATE()获取实际时间并计算某些日期与实际日期的差异:

        select datediff(day,'1997-10-07', getdate() )
        

        3) 另一个重要函数是DATEADD(),用于使用与 datediff 相同的 datepart 转换日期时间中的某些值,您可以添加(使用正值)或减去(使用负值) ) 到一个基准日期:

        select DATEADD(day,  45, getdate()) -- actual datetime adding 45 days
        select DATEADD(  s,-638, getdate()) -- actual datetime subtracting 10 minutes and 38 seconds
        

        4) 函数CONVERT() 用于格式化您需要的日期,它不是参数函数,但您可以使用部分结果来格式化您需要的结果:

        select convert(  char(8), getdate() ,   8) -- part hh:mm:ss of actual datetime
        select convert(  varchar, getdate() , 112) -- yyyymmdd
        select convert( char(10), getdate() ,  20) -- yyyy-mm-dd limited by 10 characters
        

        DATETIME 以秒为单位计算,混合这四个函数的一个有趣结果是显示两个日期之间的格式化差异 um 小时、分钟和秒 (hh:mm:ss):

        declare  @date1 datetime, @date2 datetime
        set @date1=DATEADD(s,-638,getdate())
        set @date2=GETDATE()
        
        select convert(char(8),dateadd(s,datediff(s,@date1,@date2),'1900-1-1'),8)
        

        ...结果是 00:10:38(638s = 600s + 38s = 10 分 38 秒)

        另一个例子:

        select distinct convert(char(8),dateadd(s,datediff(s, CRDATE , GETDATE() ),'1900-1-1'),8) from sysobjects order by 1
        

        【讨论】:

          【解决方案5】:

          我尝试过这种方法,它奏效了。我使用的是 SQL Server 2016 版

          SELECT DATEDIFF(MILLISECOND,'2010-01-22 15:29:55.090', '2010-01-22 15:30:09.153')/1000.00;
          

          不同的 DATEDIFF 函数有:

          SELECT DATEDIFF(year,        '2005-12-31 23:59:59.9999999', '2006-01-01 00:00:00.0000000');
          SELECT DATEDIFF(quarter,     '2005-12-31 23:59:59.9999999', '2006-01-01 00:00:00.0000000');
          SELECT DATEDIFF(month,       '2005-12-31 23:59:59.9999999', '2006-01-01 00:00:00.0000000');
          SELECT DATEDIFF(dayofyear,   '2005-12-31 23:59:59.9999999', '2006-01-01 00:00:00.0000000');
          SELECT DATEDIFF(day,         '2005-12-31 23:59:59.9999999', '2006-01-01 00:00:00.0000000');
          SELECT DATEDIFF(week,        '2005-12-31 23:59:59.9999999', '2006-01-01 00:00:00.0000000');
          SELECT DATEDIFF(hour,        '2005-12-31 23:59:59.9999999', '2006-01-01 00:00:00.0000000');
          SELECT DATEDIFF(minute,      '2005-12-31 23:59:59.9999999', '2006-01-01 00:00:00.0000000');
          SELECT DATEDIFF(second,      '2005-12-31 23:59:59.9999999', '2006-01-01 00:00:00.0000000');
          SELECT DATEDIFF(millisecond, '2005-12-31 23:59:59.9999999', '2006-01-01 00:00:00.0000000');
          

          参考:https://docs.microsoft.com/en-us/sql/t-sql/functions/datediff-transact-sql?view=sql-server-2017

          【讨论】:

            【解决方案6】:

            好的,我们都知道答案涉及DATEDIFF()。但这只会给您带来一半的结果。如果您想以人类可读的格式(即两个 DATETIME 值之间的分钟和秒数)获得结果怎么办?

            CONVERT()DATEADD()DATEDIFF() 函数非常适合您的客户可以使用的更易于阅读的结果,而不是数字。

            CONVERT(varchar(5), DATEADD(minute, DATEDIFF(MINUTE, date1, date2), 0), 114) 
            

            这会给你类似的东西:

            HH:MM

            如果您想要更高的精度,只需增加VARCHAR()

            CONVERT(varchar(12), DATEADD(minute, DATEDIFF(MINUTE, date1, date2), 0), 114) 
            

            HH:MM.SS.MS

            【讨论】:

            • 我认为在示例中为了更精确,您还需要将“分钟”更改为“秒”
            • 哦,这不包括天数。我希望选择 CONVERT(varchar(12), DATEADD(SECOND, DATEDIFF(SECOND, '2021-02-16 18:41:31.677', '2021-02-17 20:52:51.671'), 0), 114 ) 输出 26:11:20:000 而是输出 02:11:20:000
            【解决方案7】:

            在 SQL Server 内部,日期存储为 2 个整数。第一个整数是基准日期 (1900/01/01) 之前或之后的日期数。第二个整数存储午夜后时钟滴答的数量,每个滴答为 1/300 秒。

            More info here

            因此,我经常发现比较日期的最简单方法是简单地减去它们。这处理了我 90% 的用例。例如,

            select date1, date2, date2 - date1 as DifferenceInDays
            from MyTable
            ...
            

            当我需要以天数以外的单位给出答案时,我会使用DateDiff

            【讨论】:

            • 请注意,这仅适用于旧的DATETIME 类型,不适用于DATETIMEDATETIME2。此外,返回的值将是另一个 DATETIME,因此您需要将其转换为人类可读的日期之间的天数。
            【解决方案8】:

            查看日期差异的方法有多种,比较日期/时间时还有更多方法。这是我用来获取格式为“HH:MM:SS”的两个日期之间的差异的方法:

            ElapsedTime AS
                  RIGHT('0' + CAST(DATEDIFF(S, StartDate, EndDate)        / 3600 AS VARCHAR(2)), 2) + ':'
                + RIGHT('0' + CAST(DATEDIFF(S, StartDate, EndDate) % 3600 /   60 AS VARCHAR(2)), 2) + ':'
                + RIGHT('0' + CAST(DATEDIFF(S, StartDate, EndDate) %   60        AS VARCHAR(2)), 2)
            

            我将它用于计算列,但您可以轻松地将其重写为 UDF 或查询计算。请注意,此逻辑舍入小数秒; 00:00.00 到 00:00.999 被认为是零秒,并显示为“00:00:00”。

            如果您预计月经可能会超过几天,则此代码会在需要时切换为 D:HH:MM:SS 格式:

            ElapsedTime AS
                CASE WHEN DATEDIFF(S, StartDate, EndDate) >= 359999
                    THEN
                                      CAST(DATEDIFF(S, StartDate, EndDate) / 86400        AS VARCHAR(7)) + ':'
                        + RIGHT('0' + CAST(DATEDIFF(S, StartDate, EndDate) % 86400 / 3600 AS VARCHAR(2)), 2) + ':'
                        + RIGHT('0' + CAST(DATEDIFF(S, StartDate, EndDate) %  3600 /   60 AS VARCHAR(2)), 2) + ':'
                        + RIGHT('0' + CAST(DATEDIFF(S, StartDate, EndDate) %    60        AS VARCHAR(2)), 2)
                    ELSE
                          RIGHT('0' + CAST(DATEDIFF(S, StartDate, EndDate)        / 3600 AS VARCHAR(2)), 2) + ':'
                        + RIGHT('0' + CAST(DATEDIFF(S, StartDate, EndDate) % 3600 /   60 AS VARCHAR(2)), 2) + ':'
                        + RIGHT('0' + CAST(DATEDIFF(S, StartDate, EndDate) %   60        AS VARCHAR(2)), 2)
                    END
            

            【讨论】:

              【解决方案9】:

              以下查询应该提供您正在寻找的确切内容。

              select datediff(second, '2010-01-22 15:29:55.090' , '2010-01-22 15:30:09.153')
              

              这是来自 MSDN 的链接,了解您可以使用 datediff 函数做什么。 https://msdn.microsoft.com/en-us/library/ms189794.aspx

              【讨论】:

                【解决方案10】:
                SELECT DATEDIFF(yyyy, '2011/08/25', '2017/08/25') AS DateDiff
                

                它为您提供年份中两个日期之间的差异

                这里 (2017-2011)=6 结果

                语法:

                DATEDIFF(interval, date1, date2)
                

                【讨论】:

                  【解决方案11】:

                  将此用于DD:MM:SS

                  SELECT CONVERT(VARCHAR(max), Datediff(dd, '2019-08-14 03:16:51.360', 
                           '2019-08-15 05:45:37.610')) 
                         + ':' 
                         + CONVERT(CHAR(8), Dateadd(s, Datediff(s, '2019-08-14 03:16:51.360', 
                           '2019-08-15 05:45:37.610'), '1900-1-1'), 8) 
                  

                  【讨论】:

                    【解决方案12】:

                    所以这不是我的答案,但我只是在网上搜索类似问题时发现了这个。这家伙设置了一个程序来计算小时、分钟和秒。 link 和代码:

                    --Creating Function
                    If OBJECT_ID('UFN_HourMinuteSecond') Is Not Null
                    Drop Function dbo.UFN_HourMinuteSecond
                    Go
                    Exec(
                    'Create Function dbo.UFN_HourMinuteSecond
                    (
                    @StartDateTime DateTime,
                    @EndDateTime DateTime
                    ) Returns Varchar(10) 
                    As
                    Begin
                    
                    Declare @Seconds Int,
                    @Minute Int,
                    @Hour Int,
                    @Elapsed Varchar(10)
                    
                    Select @Seconds = ABS(DateDiff(SECOND ,@StartDateTime,@EndDateTime))
                    
                    If @Seconds >= 60 
                    Begin
                    select @Minute = @Seconds/60
                    select @Seconds = @Seconds%60
                    
                    If @Minute >= 60
                    begin
                    select @hour = @Minute/60
                    select @Minute = @Minute%60
                    end
                    
                    Else
                    Goto Final 
                    End
                    
                    Final:
                    Select @Hour = Isnull(@Hour,0), @Minute = IsNull(@Minute,0), @Seconds =               IsNull(@Seconds,0)
                    select @Elapsed = Cast(@Hour as Varchar) + '':'' + Cast(@Minute as Varchar) + '':'' +     Cast(@Seconds as Varchar)
                    
                    Return (@Elapsed)
                    End'
                    )
                    

                    【讨论】:

                      【解决方案13】:
                      declare @dt1 datetime='2012/06/13 08:11:12', @dt2 datetime='2012/06/12 02:11:12'
                      
                      select CAST((@dt2-@dt1) as time(0))
                      

                      【讨论】:

                        【解决方案14】:

                        打印 DATEDIFF(秒,'2010-01-22 15:29:55.090','2010-01-22 15:30:09.153')

                        【讨论】:

                          【解决方案15】:
                          select
                          datediff(millisecond,'2010-01-22 15:29:55.090','2010-01-22 15:30:09.153') / 1000.0 as Secs
                          
                          result:
                          Secs
                          14.063
                          

                          只是想我会提到它。

                          【讨论】:

                            【解决方案16】:

                            CREATE FUNCTION getDateDiffHours(@fdate 作为日期时间,@tdate 作为日期时间) 返回 varchar (50) 作为 开始 声明@cnt int 声明 @cntDate 日期时间 声明@dayDiff int 声明@dayDiffWk int DECLARE @hrsDiff 十进制(18)

                            DECLARE @markerFDate datetime
                            DECLARE @markerTDate datetime
                            
                            DECLARE @fTime int
                            DECLARE @tTime int 
                            
                            
                            DECLARE @nfTime varchar(8)
                            DECLARE @ntTime varchar(8)
                            
                            DECLARE @nfdate datetime
                            DECLARE @ntdate datetime
                            
                            -------------------------------------
                            --DECLARE @fdate datetime
                            --DECLARE @tdate datetime
                            
                            --SET @fdate = '2005-04-18 00:00:00.000'
                            --SET @tdate = '2005-08-26 15:06:07.030'
                            -------------------------------------
                            
                            DECLARE @tempdate datetime
                            
                            --setting weekends
                            SET @fdate = dbo.getVDate(@fdate)
                            SET @tdate = dbo.getVDate(@tdate)
                            --RETURN @fdate 
                            
                            SET @fTime = datepart(hh,@fdate)
                            SET @tTime = datepart(hh,@tdate)
                            --RETURN @fTime 
                            if datediff(hour,@fdate, @tdate) <= 9
                            
                                    RETURN(convert(varchar(50),0) + ' Days ' + convert(varchar(50),datediff(hour,@fdate, @tdate)))  + ' Hours'
                            else
                            --setting working hours
                            SET @nfTime = dbo.getV00(convert(varchar(2),datepart(hh,@fdate))) + ':' +dbo.getV00(convert(varchar(2),datepart(mi,@fdate))) + ':'+  dbo.getV00(convert(varchar(2),datepart(ss,@fdate)))
                            SET @ntTime = dbo.getV00(convert(varchar(2),datepart(hh,@tdate))) + ':' +dbo.getV00(convert(varchar(2),datepart(mi,@tdate))) + ':'+  dbo.getV00(convert(varchar(2),datepart(ss,@tdate)))
                            
                            IF @fTime > 17 
                            begin
                                set @nfTime = '17:00:00'
                            end 
                            else
                            begin
                                IF @fTime < 8 
                                    set @nfTime = '08:00:00'
                            end 
                            
                            IF @tTime > 17 
                            begin
                                set @ntTime = '17:00:00'
                            end 
                            else
                            begin
                                IF @tTime < 8 
                                    set @ntTime = '08:00:00'
                            end 
                            
                            
                            
                            -- used for working out whole days
                            
                            SET @nfdate = dateadd(day,1,@fdate) 
                            
                            SET @ntdate = @tdate
                            SET @nfdate = convert(varchar,datepart(yyyy,@nfdate)) + '-' + convert(varchar,datepart(mm,@nfdate)) + '-' + convert(varchar,datepart(dd,@nfdate))
                            SET @ntdate = convert(varchar,datepart(yyyy,@ntdate)) + '-' + convert(varchar,datepart(mm,@ntdate)) + '-' + convert(varchar,datepart(dd,@ntdate))
                            SET @cnt = 0
                            SET @dayDiff = 0 
                            SET @cntDate = @nfdate
                            SET @dayDiffWk = convert(decimal(18,2),@ntdate-@nfdate)
                            
                            --select @nfdate,@ntdate
                            
                            WHILE @cnt < @dayDiffWk
                            BEGIN   
                                IF (NOT DATENAME(dw, @cntDate) = 'Saturday') AND (NOT DATENAME(dw, @cntDate) = 'Sunday')
                                BEGIN 
                                    SET @dayDiff = @dayDiff + 1
                                END 
                                SET @cntDate = dateadd(day,1,@cntDate)
                                SET @cnt = @cnt + 1
                            END 
                            
                            --SET @dayDiff = convert(decimal(18,2),@ntdate-@nfdate) --datediff(day,@nfdate,@ntdate)
                            --SELECT @dayDiff
                            
                            set @fdate = convert(varchar,datepart(yyyy,@fdate)) + '-' + convert(varchar,datepart(mm,@fdate)) + '-' + convert(varchar,datepart(dd,@fdate)) + ' ' + @nfTime
                            set @tdate = convert(varchar,datepart(yyyy,@tdate)) + '-' + convert(varchar,datepart(mm,@tdate)) + '-' + convert(varchar,datepart(dd,@tdate)) + ' ' + @ntTime
                            
                            set @markerFDate = convert(varchar,datepart(yyyy,@fdate)) + '-' + convert(varchar,datepart(mm,@fdate)) + '-' + convert(varchar,datepart(dd,@fdate)) + ' ' + '17:00:00'
                            set @markerTDate = convert(varchar,datepart(yyyy,@tdate)) + '-' + convert(varchar,datepart(mm,@tdate)) + '-' + convert(varchar,datepart(dd,@tdate)) + ' ' + '08:00:00'
                            
                            --select @fdate,@tdate
                            --select @markerFDate,@markerTDate
                            
                            set @hrsDiff = convert(decimal(18,2),datediff(hh,@fdate,@markerFDate))
                            
                            --select @hrsDiff
                            set @hrsDiff = @hrsDiff +  convert(int,datediff(hh,@markerTDate,@tdate))
                            
                            --select @fdate,@tdate  
                            
                            IF convert(varchar,datepart(yyyy,@fdate)) + '-' + convert(varchar,datepart(mm,@fdate)) + '-' + convert(varchar,datepart(dd,@fdate)) = convert(varchar,datepart(yyyy,@tdate)) + '-' + convert(varchar,datepart(mm,@tdate)) + '-' + convert(varchar,datepart(dd,@tdate))  
                            BEGIN
                                --SET @hrsDiff = @hrsDiff - 9
                                Set @hrsdiff = datediff(hour,@fdate,@tdate)
                            END 
                            
                            --select FLOOR((@hrsDiff / 9))
                            
                            IF (@hrsDiff / 9) > 0 
                            BEGIN
                                SET @dayDiff = @dayDiff + FLOOR(@hrsDiff / 9)
                                SET @hrsDiff = @hrsDiff - FLOOR(@hrsDiff / 9)*9
                            END 
                            
                            --select convert(varchar(50),@dayDiff) + ' Days ' + convert(varchar(50),@hrsDiff)   + ' Hours'
                            
                            RETURN(convert(varchar(50),@dayDiff) + ' Days ' + convert(varchar(50),@hrsDiff))    + ' Hours'
                            

                            结束

                            【讨论】:

                            • 你能根据问题解释一下你的代码吗?
                            【解决方案17】:

                            Sol-1:

                            select 
                              StartTime
                              , EndTime
                              , CONVERT(NVARCHAR,(EndTime-StartTime), 108) as TimeDiff 
                            from 
                              [YourTable]
                            

                            Sol-2:

                            select 
                              StartTime
                              , EndTime
                              , DATEDIFF(hh, StartTime, EndTime)
                              , DATEDIFF(mi, StartTime, EndTime) % 60 
                            from 
                              [YourTable]
                            

                            Sol-3:

                            select 
                              DATEPART(hour,[EndTime]-[StartTime])
                              , DATEPART(minute,[EndTime]-[StartTime]) 
                            from 
                              [YourTable]
                            

                            日期部分效果最好

                            【讨论】:

                              【解决方案18】:

                              请检查以下技巧以找出两个日期之间的日期差异

                               DATEDIFF(DAY,ordr.DocDate,RDR1.U_ProgDate) datedifff
                              

                              您可以根据需要更改日期或月份或年份或时间的差异。

                              【讨论】:

                                【解决方案19】:

                                对我来说这非常有效 转换(varchar(8),DATEADD(SECOND,DATEDIFF(SECOND,LogInTime,LogOutTime),0),114)

                                输出是 HH:MM:SS 在我的情况下准确显示。

                                【讨论】:

                                  【解决方案20】:

                                  请尝试

                                  DECLARE @articleDT DATETIME;
                                  DECLARE @nowDate DATETIME;
                                   
                                  -- Time of the ARTICLE created
                                  SET @articleDT = '2012-04-01 08:10:16';
                                   
                                  -- Simulation of NOW datetime
                                  -- (in real world you would probably use GETDATE())
                                  SET @nowDate = '2012-04-10 11:35:36';
                                   
                                  -- Created 9 days ago.
                                  SELECT 'Created ' + CAST(DATEDIFF(day, @articleDT, @nowDate) AS NVARCHAR(50)) + ' days ago.';
                                   
                                  -- Created 1 weeks, 2 days, 3 hours, 25 minutes and 20 seconds ago.
                                  SELECT 'Created '
                                      + CAST(DATEDIFF(second, @articleDT, @nowDate) / 60 / 60 / 24 / 7 AS NVARCHAR(50)) + ' weeks, '
                                      + CAST(DATEDIFF(second, @articleDT, @nowDate) / 60 / 60 / 24 % 7 AS NVARCHAR(50)) + ' days, '
                                      + CAST(DATEDIFF(second, @articleDT, @nowDate) / 60 / 60 % 24  AS NVARCHAR(50)) + ' hours, '
                                      + CAST(DATEDIFF(second, @articleDT, @nowDate) / 60 % 60 AS NVARCHAR(50)) + ' minutes and '
                                      + CAST(DATEDIFF(second, @articleDT, @nowDate) % 60 AS NVARCHAR(50)) + ' seconds ago.';
                                  

                                  【讨论】:

                                    【解决方案21】:

                                    在 Books Online 上查看 DateDiff。

                                    【讨论】:

                                      猜你喜欢
                                      • 1970-01-01
                                      • 2018-08-01
                                      • 2021-10-21
                                      • 2015-06-21
                                      • 1970-01-01
                                      • 2023-03-08
                                      • 1970-01-01
                                      • 1970-01-01
                                      • 1970-01-01
                                      相关资源
                                      最近更新 更多