sql server 日期

网上取当月第一天和最后一天的SQL语句很多,有的是通过字符截取,有的是通过函数,个人还是比较偏向于使用内置函数来处理,

但是看了下网上的运用函数来取第一天和最后一天时间的SQL语句几乎都像下面这样的,其实是存在问题的,存在一个临界值得问题。


     本月第一天:select   dateadd(dd,-day(getdate())+1,getdate())  

   本月最后一天:select   dateadd(dd,-day(getdate()),dateadd(m,1,getdate()))
      上面的两句,第一句取第一天的完全没问题,第二句就有问题了,一般的想法是取最后一天,可以在当前时间上加一个月,然后减去当前时间的天数,比如随便 2009-8-27,加一个月就是2009-9-27,然后减去2009-8-27时间的天数27天 正好是2009-8-31,没问题呀。

       但是,如果当前时间本身就是最后一天的话,就会产生临界问题了,比如传入的实际是2009-5-31,最终得到的最后一天的时间其实也应该是 2009-5-31才对,如果按照上面的写法,2009-5-31加一个月是多少,2009-6-31?2009-7-1?都不是,由于月大月小的问 题,6月份只有30天,所以2009-5-31加一个月后是2009-6-30日,还是按上面的写法然后再减去2009-5-31时间的天数31天,最终 得到的最后一天是2009-5-30,傻眼了,咋回事啊?

        还有2月只有28或29天当然也会存在这样的问题,只要稍微改动一下,在减天数的时候不应减当前时间的天数,而应减去加了月份之后的天数,如下写法:
        select   dateadd(dd,-day(dateadd(m,1,getdate())),dateadd(m,1,getdate()))

        这样的话,即使6月没有31天,2009-6-30减去30天就是2009-5-31,再如2009-1-30加一个月是2009-2-28,减去28天后是2009-1-31符合正确性。

可以依此类推:


可以依此类推:

select   dateadd(dd,-day(dateadd(month,-1,getdate()))+1,dateadd(month,-1,getdate()))     /*上个月一号*/
select   dateadd(dd,-day(getdate()),getdate())                                                                      /* 上月月底 */
select   dateadd(dd,-day(getdate())+1,getdate())                                                                  /* 本月一号 */
select   dateadd(dd,-day(dateadd(month,1,getdate())),dateadd(month,1,getdate()))            /* 本月底 */
select   dateadd(dd,-day(dateadd(month,1,getdate()))+1,dateadd(month,1,getdate()))        /* 下月一号 */
select   dateadd(dd,-day(dateadd(month,2,getdate())),dateadd(month,2,getdate()))            /* 下月月底 */

如果想把时间格式转换成“yyyy/mm/dd hh:mi:ss”这种格式,可以:

select rtrim(convert(char,getdate(),111))+''+(convert(char,getdate(),108))  -- yyyy/mm/dd hh:mi:ss


测试:(列出上月开始和结束时间,然后转换时间格式)
 declare @time1 datetime,
              @time2 datetime,
              @time3  datetime,
              @time4 datetime

 
         set @time1 = dateadd(dd,-day(dateadd(month,-1,getdate()))+1,dateadd(month,-1,getdate())),    --上个月一号
               @time2 = dateadd(dd,-day(getdate())+1,getdate())               --本月一号
         set @time3 = rtrim(convert(char,@time1,111))+''+(convert(char,@time1,108)),
               @time4 = rtrim(convert(char,@time2,111))+''+(convert(char,@time2,108))
 
        select dateadd(dd,-day(dateadd(month,-1,getdate()))+1,dateadd(month,-1,getdate()))   
        select dateadd(dd,-day(getdate())+1,getdate()) 
        select rtrim(convert(char,@time1,111))+''+(convert(char,@time1,108))  -- yyyy/mm/dd hh:mi:ss
        select rtrim(convert(char,@time2,111))+''+(convert(char,@time2,108))  -- yyyy/mm/dd hh:mi:ss


输出结果:(sybase下)
Jan  1 2011  5:30PM                              
-                              
Feb  1 2011  5:30PM                                                                      
-                                                             
2011/01/01 17:30:58                                                                                                    
-                                                             
2011/02/01 17:30:58       

------==========T-SQL 常用星期设置============-------




--所在星期的第一天,计算给定日期所在星期的第1天(星期日为第一天) 
DECLARE @Date  DATETIME
SET @Date= GETDATE()
--与SQL Server语言版本相关的算法
--思路:当前日期+星期日(每周的第1天)与当前日期的差的天数
--DATEPART(WEEKDAY,DATE)的返回值与@@DATEFIRST相关
SET DATEFIRST 7 -- 或者设置为美国英语SET LANGUAGE us_english; (星期日为第一天)
SELECT DATEADD(WEEKDAY,1-DATEPART(WEEKDAY,@Date),@Date) AS 所在星期的第一天
--星期日,与SQL Server语言版本或@@DATEFIRST无关
--1899-12-31 是星期日,1899-12-31 再加上(当前日期与 1899-12-31差的星期数)个星期
SELECT DATEADD(WEEK,DATEDIFF(WEEK,-1,@Date),-1) AS 所在星期的星期日
--或者
SELECT DATEADD(WEEK,DATEDIFF(WEEK,6,@Date),6) AS 所在星期的星期日
GO


--所在星期的第二天,计算给定日期所在星期的第2天(星期日为第一天)
DECLARE @Date  DATETIME
SET @Date= GETDATE()
--DATEPART(WEEKDAY,DATE)的返回值与@@DATEFIRST相关
SET DATEFIRST 7 -- 
SELECT DATEADD(DAY,2-DATEPART(WEEKDAY,@Date),@Date) AS 所在星期的第二天
--'1900-01-01' 是星期一,'1900-01-01' 再加上(当前日期与'1900-01-01'差的星期数)个星期
SELECT DATEADD(WEEK,DATEDIFF(WEEK,0,@Date),0) AS 所在星期的星期一
GO

--上个星期第一天,计算给定日期所在星期的上一个星期日(星期日为第一天)
DECLARE @Date  DATETIME
SET @Date= GETDATE()
--思路:当前日志所在星期的星期日再减1周
--DATEPART(WEEKDAY,DATE)的返回值与@@DATEFIRST相关
--SET DATEFIRST 7 -- 或者设置为美国英语SET LANGUAGE us_english; (星期日为第一天)
SELECT DATEADD(WEEK,-1,DATEADD(DAY,1-DATEPART(WEEKDAY,@Date),@Date)) AS 上个星期第一天
--一周等于7天
SELECT DATEADD(DAY,-7,DATEADD(DAY,1-DATEPART(WEEKDAY,@Date),@Date)) AS 上个星期第一天
--简化
SELECT DATEADD(DAY,-6-DATEPART(WEEKDAY,@Date),@Date) AS 上个星期第一天
--上个星期日,与SQL Server语言版本或@@DATEFIRST无关
SELECT DATEADD(WEEK,-1+DATEDIFF(WEEK,-1,@Date),-1) AS 上个星期日
--或者
SELECT DATEADD(WEEK,DATEDIFF(WEEK,6,@Date),-1) AS 上个星期日
GO


--下个星期第一天,计算给定日期所在星期的下一个星期日(星期日为第一天)
DECLARE @Date  DATETIME
SET @Date= GETDATE()
SET DATEFIRST 7 
SELECT DATEADD(WEEK,1,DATEADD(DAY,1-DATEPART(WEEKDAY,@Date),@Date)) AS 下个星期第一天
--一周等于7天
SELECT DATEADD(DAY,7,DATEADD(DAY,1-DATEPART(WEEKDAY,@Date),@Date)) AS 下个星期第一天
--简化
SELECT DATEADD(DAY,8-DATEPART(WEEKDAY,@Date),@Date) AS 下个星期第一天
--下个星期日,与SQL Server语言版本或@@DATEFIRST无关
SELECT DATEADD(WEEK,1+DATEDIFF(WEEK,-1,@Date),-1) AS 下个星期日
--或者
SELECT DATEADD(WEEK,DATEDIFF(WEEK,-1,@Date),6) AS 下个星期日
GO

--判断给定日期是星期几
DECLARE @Date  DATETIME
SET @Date= GETDATE()
--DATEPART(WEEKDAY,DATE)的返回值与@@DATEFIRST相关
SET DATEFIRST 7 -- 或者设置为美国英语SET LANGUAGE us_english; (星期日为第一天)
SELECT DATEPART(WEEKDAY,@Date) --返回值 1-星期日,2-星期一,3-星期二......7-星期六
--上面算法与SQL 语言版本或 @@DATEFIRST 相关
--下面算法与SQL Server语言版本或@@DATEFIRST无关
SELECT DATENAME(WEEKDAY,@Date) 星期 
GO

  

在本文中,GetDate()获得的日期由两部分组成,分别是今天的日期和当时的时间: Select GetDate() 
用DateName()就可以获得相应的年、月、日,然后再把它们连接起来就可以了:

Select Datename(year,GetDate())+'-'+Datename
(month,GetDate())+'-'+Datename(day,GetDate())

另外,DateName()还可以获得到小时、时间、秒、星期几、第几周,分别如下:

Select Datename(hour,GetDate())
Select Datename(minute,GetDate())
Select Datename(second,GetDate())
Select Datename(weekDay,GetDate())
Select Datename(week,GetDate())

SQL中的日期类型DateTime的默认格式就是yyyy-mm-dd hh:mi:ss: mmm,可大多数的情况我们只想得到他的日期部分,而不许要后面的时间。上一篇中提到用Datename()函数来截取拼接出不包含时间部分的日期,现在再说一种方法,更加简单的获取到不包含时间的日期!


使用Convert()函数:

select convert(char(10),GetDate(),120) as Date

* 第3个参数就是用来设置日期类型数据的显示样式的,下面介绍几种样式的参数:

100   mm dd yyyy

101   mm/dd/yyyy

102   yyyy.mm.dd

103   dd/mm/yyyy

106   dd mm yyyy

108   hh:mi:ss(时间)

111   yyyy/mm/dd

112   yyyymmdd

120   yyyy-mm-dd

DECLARE @ThisWeekStartTime NVARCHAR(100),@ThisWeekEndTime NVARCHAR(100),--本周
            @LastWeekStartTime NVARCHAR(100),@LastWeekEndTime NVARCHAR(100),--上周
            @ThisMonthStartTime NVARCHAR(100),@ThisMonthEndTime  NVARCHAR(100),--本月
            @LastMonthSartTime NVARCHAR(100),@LastMonthEndTime NVARCHAR(100),--上月
            @LastestHalfYearStartTime NVARCHAR(100),@LastestHalfYearEndTime NVARCHAR(100),--近半年
            @LastestOneYearStartTime NVARCHAR(100),@LastestOneYearEndTime NVARCHAR(100)--近一年
            
    SELECT @ThisWeekStartTime= CONVERT(nvarchar(10), DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, -1, getdate()) ), 0),121)--本周开始时间
    SELECT @ThisWeekEndTime= CONVERT(nvarchar(10), DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, -1, getdate()) ), 6),121)--本周结束时间
    
    SELECT @LastWeekStartTime=  CONVERT(nvarchar(10),DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, -7, getdate()) ), 0),121)--上周开始时间
    SELECT @LastWeekEndTime= CONVERT(nvarchar(10), DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, -7, getdate()) ), 6),121)--上周结束时间
     
    SELECT @ThisMonthStartTime=CONVERT(nvarchar(10),dateadd(dd,-day(getdate())+1,getdate()),121)--本月开始时间
    SELECT @ThisMonthEndTime=CONVERT(nvarchar(10),dateadd(dd,-day(getdate()),dateadd(m,1,getdate())),121)--本月结束时间
    
    SELECT @LastMonthSartTime=CONVERT(nvarchar(10),dateadd(dd,-day(dateadd(month,-1,getdate()))+1,dateadd(month,-1,getdate())),121)--上月开始时间
    SELECT @LastMonthEndTime= CONVERT(nvarchar(10), dateadd(dd,-day(getdate()),getdate()),121) --上月结束时间
 
    SELECT @LastestHalfYearStartTime= CONVERT(nvarchar(10),  dateadd(dd,-day(dateadd(month,-6,getdate()))+1,dateadd(month,-6,getdate())) ,121)--近半年开始时间
    SELECT @LastestHalfYearEndTime=CONVERT(nvarchar(10), dateadd(dd,-day(getdate()),getdate()),121)--近半年结束时间
    
    SELECT @LastestOneYearStartTime= CONVERT(nvarchar(10), dateadd(dd,-day(dateadd(month,-12,getdate()))+1,dateadd(month,-12,getdate())) ,121)--近一年开始时间
    SELECT @LastestOneYearEndTime=CONVERT(nvarchar(10), dateadd(dd,-day(getdate()),getdate()),121)--近一年结束时

  

复制代码
1 SELECT CONVERT(varchar(100), GETDATE(), 0) 05 9 2011 9:12AM
2  SELECT CONVERT(varchar(100), GETDATE(), 1) 05/09/11
3 SELECT CONVERT(varchar(100), GETDATE(), 2) 11.05.09
4 SELECT CONVERT(varchar(100), GETDATE(), 3) 09/05/11
5 SELECT CONVERT(varchar(100), GETDATE(), 4) 09.05.11
6 SELECT CONVERT(varchar(100), GETDATE(), 5) 09-05-11
7 SELECT CONVERT(varchar(100), GETDATE(), 6) 09 05 11
8 SELECT CONVERT(varchar(100), GETDATE(), 7) 05 09, 11
9 SELECT CONVERT(varchar(100), GETDATE(), 8) 09:13:14
10 SELECT CONVERT(varchar(100), GETDATE(), 9) 05 9 2011 9:13:14:670AM
11 SELECT CONVERT(varchar(100), GETDATE(), 10) 05-09-11
12 SELECT CONVERT(varchar(100), GETDATE(), 11) 11/05/09
13 SELECT CONVERT(varchar(100), GETDATE(), 12) 110509
14 SELECT CONVERT(varchar(100), GETDATE(), 13) 09 05 2011 09:13:14:670
15 SELECT CONVERT(varchar(100), GETDATE(), 14) 09:13:14:670
16 SELECT CONVERT(varchar(100), GETDATE(), 20) 2011-05-09 09:13:14
17 SELECT CONVERT(varchar(100), GETDATE(), 21) 2011-05-09 09:13:14.670
18 SELECT CONVERT(varchar(100), GETDATE(), 22) 05/09/11 9:15:33 AM
19 SELECT CONVERT(varchar(100), GETDATE(), 23) 2011-05-09
20 SELECT CONVERT(varchar(100), GETDATE(), 24) 09:15:33
21 SELECT CONVERT(varchar(100), GETDATE(), 25) 2011-05-09 09:15:33.140
22 SELECT CONVERT(varchar(100), GETDATE(), 100) 05 9 2011 9:15AM
23 SELECT CONVERT(varchar(100), GETDATE(), 101) 05/09/2011
24 SELECT CONVERT(varchar(100), GETDATE(), 102) 2011.05.09
25 SELECT CONVERT(varchar(100), GETDATE(), 103) 09/05/2011
26 SELECT CONVERT(varchar(100), GETDATE(), 104) 09.05.2011
27 SELECT CONVERT(varchar(100), GETDATE(), 105) 09-05-2011
28 SELECT CONVERT(varchar(100), GETDATE(), 106) 09 05 2011
29 SELECT CONVERT(varchar(100), GETDATE(), 107) 05 09, 2011
30 SELECT CONVERT(varchar(100), GETDATE(), 108) 09:16:38
31 SELECT CONVERT(varchar(100), GETDATE(), 109) 05 9 2011 9:16:38:543AM
32 SELECT CONVERT(varchar(100), GETDATE(), 110) 05-09-2011
33 SELECT CONVERT(varchar(100), GETDATE(), 111) 2011/05/09
34 SELECT CONVERT(varchar(100), GETDATE(), 112) 20110509
35 SELECT CONVERT(varchar(100), GETDATE(), 113) 09 05 2011 09:17:19:857
36 SELECT CONVERT(varchar(100), GETDATE(), 114) 09:17:19:857
37 SELECT CONVERT(varchar(100), GETDATE(), 120) 2011-05-09 09:17:19
38 SELECT CONVERT(varchar(100), GETDATE(), 121) 2011-05-09 09:17:19.857
39 SELECT CONVERT(varchar(100), GETDATE(), 126) 2011-05-09T09:17:19.857
40 SELECT CONVERT(varchar(100), GETDATE(), 130) 6 ????? ??????? 1432 9:17:19:857AM
41 SELECT CONVERT(varchar(100), GETDATE(), 131) 6/06/1432 9:17:19:857AM
复制代码
原文地址:https://www.cnblogs.com/ethan-song/p/5892036.html