一、日期推算
1--指定日期该年的第一天或最后一天 ?年的第一天 SELECT CONVERT(char(5),@dt,120)+'1-1'
?年的最后一天 SELECT CONVERT(char(5),120)+'12-31'
2--指定日期所在季度的第一天或最后一天 季度的第一天 SELECT CONVERT(datetime, ?CONVERT(char(8), ??DATEADD(Month, ???DATEPART(Quarter,@dt)*3-Month(@dt)-2, ???@dt), ??120)+'1')
?季度的最后一天(CASE判断法) SELECT CONVERT(datetime,@dt)*3-Month(@dt), ??120) ?+CASE WHEN DATEPART(Quarter,@dt) in(1,4) ??THEN '31'ELSE '30' END)
季度的最后一天(直接推算法) SELECT DATEADD(Day,-1, ???1+DATEPART(Quarter, ??120)+'1')
3--指定日期所在月份的第一天或最后一天 月的第一天 SELECT CONVERT(datetime,CONVERT(char(8),120)+'1')
月的最后一天 SELECT DATEADD(Day,DATEADD(Month,1,@dt),120)+'1')
月的最后一天(容易使用的错误方法) SELECT DATEADD(Month,DATEADD(Day,-DAY(@dt),@dt))
4--指定日期所在周的任意一天 SELECT DATEADD(Day,@number-DATEPART(Weekday,@dt)
5--指定日期所在周的任意星期几 ?星期天做为一周的第1天 SELECT DATEADD(Day,@number-(DATEPART(Weekday,@dt)+@@DATEFIRST-1)%7,@dt)
?星期一做为一周的第1天 SELECT DATEADD(Day,@dt)+@@DATEFIRST-2)%7-1,@dt)
二、特殊日期
--特殊日期加减函数
?对于日期指定部分的加减,使用DATEADD函数就可以轻松实现。 ?在实际的处理中,还有一种比较另类的日期加减处理 ?就是在指定的日期中,加上(或者减去)多个日期部分 ?比如将2005年3月11日,加上1年3个月11天2小时。 ?对于这种日期的加减处理,DATEADD函数的力量就显得有点不够。
?本函数实现这样格式的日期字符串加减处理: ?y-m-d h:m:s.m | -y-m-d h:m:s.m ?说明: ?要加减的日期字符输入方式与日期字符串相同。日期与时间部分用空格分隔 ?最前面一个字符如果是减号(-)的话,表示做减法处理,否则做加法处理。 ?如果日期字符只包含数字,则视为日期字符中,仅包含天的信息。 CREATE FUNCTION dbo.f_DateADD( @Date???? datetime, @DateStr?? varchar(23) )RETURNS datetime AS BEGIN ?DECLARE @bz int,@s varchar(12),@i int
?IF @DateStr IS NULL OR @Date IS NULL ??OR(CHARINDEX('.',@DateStr)>0 ???AND @DateStr NOT LIKE '%[:]%[:]%.%') ??RETURN(NULL) ?IF @DateStr='' RETURN(@Date)
?SELECT @bz=CASE ???WHEN LEFT(@DateStr,1)='-' THEN -1 ???ELSE 1 END, ??@DateStr=CASE ???WHEN LEFT(@Date,1)='-' ???THEN STUFF(RTRIM(LTRIM(@DateStr)),'') ???ELSE RTRIM(LTRIM(@DateStr)) END
?IF CHARINDEX(' ',@DateStr)>1 ??OR CHARINDEX('-',@DateStr)>1 ??OR(CHARINDEX('.',@DateStr)=0 ???AND CHARINDEX(':',@DateStr)=0) ?BEGIN ??SELECT @i=CHARINDEX(' ',@DateStr+' ') ???,@s=REVERSE(LEFT(@DateStr,@i-1))+'-' ???,@DateStr=STUFF(@DateStr,@i,'') ???,@i=0 ??WHILE @s>'' and @i<3 ???SELECT @Date=CASE @i ?????WHEN 0 THEN DATEADD(Day,@bz*REVERSE(LEFT(@s,CHARINDEX('-',@s)-1)),@Date) ?????WHEN 1 THEN DATEADD(Month,@Date) ?????WHEN 2 THEN DATEADD(Year,@Date) ????END, ????@s=STUFF(@s,@s),''), ????@i=@i+1???? ?END ?IF @DateStr>'' ?BEGIN ??IF CHARINDEX('.',@DateStr)>0 ???SELECT @Date=DATEADD(Millisecond ?????,@bz*STUFF(@DateStr,CHARINDEX('.',@DateStr), ?????@Date), ????@DateStr=LEFT(@DateStr,@DateStr)-1)+':', ????@i=0 ??ELSE ???SELECT @DateStr=@DateStr+':',@i=0 ??WHILE @DateStr>'' and @i<3 ???SELECT @Date=CASE @i ?????WHEN 0 THEN DATEADD(Hour,@bz*LEFT(@DateStr,CHARINDEX(':',@DateStr)-1),@Date) ?????WHEN 1 THEN DATEADD(Minute,@Date) ?????WHEN 2 THEN DATEADD(Second, ????@DateStr=STUFF(@DateStr, ????@i=@i+1 ?END
?RETURN(@Date) END GO
三、计算工作时间
1--定义工作时间表 CREATE TABLE tb_worktime( ?ID?????? int identity(1,1) PRIMARY KEY,??????????? --序号 ?time_start smalldatetime,??????????????????????????? --工作的开始时间 ?time_end? smalldatetime,?????????????????????????? --工作的结束时间 ?worktime? AS DATEDIFF(Minute,time_start,time_end)? --工作时数(分钟) ) GO
if exists (select * from dbo.sysobjects where id = object_id(N'[dbo].[f_WorkTime]') and xtype in (N'FN',N'IF',N'TF')) drop function [dbo].[f_WorkTime] GO
2--计算两个日期之间的工作时间 CREATE FUNCTION f_WorkTime( @date_begin datetime,? --计算的开始时间 @date_end datetime???? --计算的结束时间 )RETURNS int AS BEGIN ?DECLARE @worktime int ?IF DATEDIFF(Day,@date_begin,@date_end)=0 ??SELECT @worktime=SUM(DATEDIFF(Minute,???CASE WHEN CONVERT(VARCHAR,108)>time_start ????THEN CONVERT(VARCHAR,108) ????ELSE time_start END,@date_end,108)<time_end ????THEN CONVERT(VARCHAR,108) ????ELSE time_end END)) ??FROM tb_worktime ??WHERE time_end>CONVERT(VARCHAR,108) ???AND time_start<CONVERT(VARCHAR,108) ?ELSE ??SET @worktime ???=(SELECT SUM(CASE ?????WHEN CONVERT(VARCHAR,108)>time_start ?????THEN DATEDIFF(Minute,CONVERT(VARCHAR,108),time_end) ?????ELSE worktime END) ????FROM tb_worktime ????WHERE time_end>CONVERT(VARCHAR,108)) ???+(SELECT SUM(CASE ?????WHEN CONVERT(VARCHAR,108)<time_end ?????THEN DATEDIFF(Minute,108)) ?????ELSE worktime END) ????FROM tb_worktime ????WHERE time_start<CONVERT(VARCHAR,108)) ???+CASE ????WHEN DATEDIFF(Day,@date_end)>1 ????THEN (DATEDIFF(Day,@date_end)-1) ?????*(SELECT SUM(worktime) FROM tb_worktime) ????ELSE 0 END ?RETURN(@worktime) END
(编辑:李大同)
【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!
|