数据库之SQL技巧整理案例

一、获得给定月份的周日数

根据给定的某个日期,计算这个月份的周日的天数。
根据系统变量@@datefirst的值,判断周日的序号为【datepart(weekday,rq)= (07-@@datefirst) % 7 + 1】。下面列出了周日、周一…周六的公式

公式 周几
(7-@@datefirst)%7 +1 周日
(7-@@datefirst)%7 +2 周一
(7-@@datefirst)%7 +3 周二
(7-@@datefirst)%7 +4 周三
(7-@@datefirst)%7 +5 周四
(7-@@datefirst)%7 +6 周五
(7-@@datefirst)%7 +7 周六

下面是获得周日的sql语句,sql语句采用了嵌套循环的方式来获取数据

declare @day smalldatetime
set @day = dateadd(mm, datediff(mm,0,'2019-11-21'), 0)

;with temp as
(  select @day as rq union all
    select rq+1
    from temp where datediff(month,rq+1,@day) = 0
)
select
    rn = row_number() over(order by rq),
    rq
from temp where datepart(weekday,rq)= (07-@@datefirst) % 7 + 1

其中:

【dateadd(mm, datediff(mm,0,‘2019-08-21′), 0)】是获取当月第一天的通常做法
运行结果如下:

+—+———————+

|rn | rq                  |

|—+———————|

| 1 | 2019-08-04 00:00:00 |

| 2 | 2019-08-11 00:00:00 |

| 3 | 2019-08-18 00:00:00 |

| 4 | 2019-08-25 00:00:00 |

+—+———————+

二、获得给定月份的所有天的日期

其中:
【datediff(month,fday+1,@rq) = 0】是判断月份相等的通常做法

declare @rq smalldatetime
set @rq = '2019-09-01';

;with
  tappdays (fday) as
  (
    select @rq as fday
    union all
    select fday + 1 from tappdays where datediff(month,fday+1,@rq) = 0
  )
select * from tappdays order by fday

下面是运行结果

fday

———————

2019-09-01 00:00:00

2019-09-02 00:00:00

2019-09-03 00:00:00

2019-09-23 00:00:00

2019-09-24 00:00:00

2019-09-25 00:00:00

2019-09-26 00:00:00

2019-09-27 00:00:00

2019-09-28 00:00:00

2019-09-29 00:00:00

2019-09-30 00:00:00

三、获得子字符串列表

利用递归来获得给定字符串的split方法

-- 利用递归来获得给定字符串的split方法

declare @commentstr nvarchar(4000)='总经理室|销售部|会计部|人事部|工会|后勤部|生产计划部|动力分厂|质量检验部|运输部'
declare @split     nvarchar(1)='|';

with temp as
(  select 1 as num union all
   select num + 1
   from temp where num<len(@commentstr)   )
select
  rn = row_number() over(order by num),
  splitstr = substring(@commentstr,num,charindex(@split,@commentstr+@split,num)-num)
from temp where substring(@split+@commentstr,num,1) = @split option(maxrecursion 0);

下面是运行效果

rn  splitstr

————————

 1  总经理室

 2  销售部

 3  会计部

 4  人事部

 5  工会

 6  后勤部

 7  生产计划部

 8  动力分厂

 9  质量检验部

10  运输部

————————

给定一个带有分隔符的字符串,通过这个语句获得各个字段的列表。

--================================================================================================
--   pappgetsplit '|','科目名称|身份证号|学员姓名|教练编号|教练姓名|培训次数|合计次数|负责比例'
================================================================================================
if exists (select name from sysobjects where name = 'pappgetsplit' and type = 'p')
   drop procedure pappgetsplit
go
create procedure pappgetsplit
  @split             varchar(1),
  @str               nvarchar(4000)
as
  ;with temp as     -- 根据分隔符|获得字段列表
  (  select 1 as num union all
     select num + 1
     from temp where num<len(@str)   )
  select
    rn = row_number() over(order by num),
    splitstr = substring(@str,num,charindex(@split,@str+@split,num)-num)
  from temp where substring(@split+@str,num,1) = @split option(maxrecursion 0);
go

下面是运行效果

+—+———————+

|rn |  splitstr           |

|—-+———————|

| 1 |  科目名称           |

| 2 |  身份证号           |

| 3 |  学员姓名           |

| 4 |  教练编号           |

| 5 |  教练姓名           |

| 6 |  培训次数           |

| 7 |  合计次数           |

| 8 |  负责比例           |

+—+———————+

四、获得本周指定周几的日期

根据指定获得的周几,得到日期

--获得本周周一的日期
declare @z smallint
-- [1,2,3,4,5,6,7]分别代表[周一,周二,周三,周四,周五,周六,周日]
set @z=1
select
  getdate() 今天,
  datepart(weekday,getdate()) 今天序号,
  (datepart(weekday,getdate()) + @@datefirst-1)%7 今天是周几,
  dateadd(day,@z-(datepart(weekday,getdate()) + @@datefirst-1)%7,getdate()) 本周周一

到此这篇关于数据库之sql技巧整理案例的文章就介绍到这了,更多相关sql技巧内容请搜索www.887551.com以前的文章或继续浏览下面的相关文章希望大家以后多多支持www.887551.com!

(0)
上一篇 2022年3月21日
下一篇 2022年3月21日

相关推荐