加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 站长学院 > MsSql教程 > 正文

SqlServer教程—第二章(日期处理二)

发布时间:2020-12-12 14:53:13 所属栏目:MsSql教程 来源:网络整理
导读:一、日期推算 1--指定日期该年的第一天或最后一天 ?年的第一天 SELECT CONVERT(char(5),@dt,120)+'1-1' ?年的最后一天 SELECT CONVERT(char(5),120)+'12-31' 2--指定日期所在季度的第一天或最后一天 季度的第一天 SELECT CONVERT(datetime, ?CONVERT(char(8)

一、日期推算

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

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读