相关函数:
getdate()——获取当前的系统日期
DATEDIFF (datepart , startdate , enddate) ——计算时间差;
DATEADD(datepart,number,date) ——在已有日期上加天数
number是字段也可以,上面有写;如果number是负数的话相当于减去天数
datepart值:year | quarter | month | week | day | hour | minute | second | millisecond
DATE_SUB(date,INTERVAL expr type) ——日期减去指定时间间隔(MySQL)
date 参数是合法的日期表达式。expr 参数是希望添加的时间间隔。
type值:类型
例:DATE_SUB(OrderDate,INTERVAL 5 DAY)
日期的输入 ‘2005-12-16 23:32:48’
1.已知开始时间RISK_START_DATE和持续的时间RISK_DURATION求出结束的时间。
SELECT DATEADD (day, RISK_DURATION, RISK_START_DATE )
AS RISK_END_DATE
FROM CONSTRUCTION_RISK
2.通过给的PLAN_START_DATE和PLAN_END_DATE判断项目进度,分别是“X月内即将进入”,“进行中”,“已完成”三个状态。
我之前写的:(提示:通过与系统时间进行对比来判断)
SELECT CASE
WHEN getdate()<RISK_START_DATE
THEN DATEDIFF(month,RISK_START_DATE,getdate())+'月内即将进入'
WHEN getdate()>=RISK_START_DATE AND getdate()<RISK_END_DATE
THEN '进行中'
WHEN getdate()>=RISK_END_DATE
THEN '已完成' END
AS 'Process' -- 注意这里并不需要加单引号
SF写的完整的一段:(尽量不要出现中文字符,这里用不同的数值来代替)
SELECT RISK_START_DATE, RISK_END_DATE, RISK_DURATION, CASE
WHEN getdate()<RISK_START_DATE
THEN DATEDIFF(month,RISK_START_DATE,getdate())
WHEN getdate()>=RISK_START_DATE AND getdate()<RISK_END_DATE
THEN '-1'
WHEN getdate()>=RISK_END_DATE
THEN '-2' ELSE NULL END
AS Process
只要对返回的数值进行说明,前端人员就能照此显示相应的字。
第一句判断结果直接加上“月内即将进入”
后两句中,“-1”表示“进行中”,“-2”表示已完成。
3.已知“隐患开始时间”RISK_START_DATE和“经过时间”RISK_DURATION,求出未来八周内每一周所包含的隐患数。
思路:要通过当前时间来计算下周的开始时间和结束时间,以此类推,得出八周的起始时间和结束时间。再通过与隐患开始和结束时间的比较来判断某一周是否存在某一个隐患。存在的话返回1,不存在的话返回0。最后可以COUNT“1”的个数,即得出每一周的隐患数。
下周周一:DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 7, getdate()) ), 0)
下周周日:DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 7, getdate()) ), 7) 不是6哦
(一周内不存在隐患的情况只可能 隐患结束时间<一周开始时间或 者是 隐患开始时间>一周结束时间,因此,要得到一周内存在隐患的情况只需要取反集就行了:
RISK_START_DATE<=一周的结束时间
AND
RISK_END_DATE>=一周的开始时间)
- 没有写“0”的情况,直接else;
- RISK_END_DATE没有写,所以只能直接在式子里用RISK_START_DATE+RISK_DURATION;
- “下周的第一天”和“下周的最后一天” 这种也是直接用式子表示,好像没法在给他别名,
不然不能直接显示 - 这里用的case when 好像就是直接和SELECT连接用的,所以直接用的SUM(….),没用COUNT(1)
最后写成这样:
SELECT SUM(CASE WHEN RISK_START_DATE<=DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 7, getdate())),7)
AND RISK_START_DATE+RISK_DURATION >= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd,7, getdate())),0)
THEN 1 ELSE 0 END) AS WEEK1,
SUM(CASE WHEN RISK_START_DATE<= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 14, getdate()) ), 7)
AND RISK_START_DATE+RISK_DURATION >= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 14, getdate()) ), 0)
THEN 1 ELSE 0 END) AS WEEK2,
SUM(CASE WHEN RISK_START_DATE<=DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 21, getdate()) ), 7)
AND RISK_START_DATE+RISK_DURATION >= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 21, getdate()) ), 0)
THEN 1 ELSE 0 END) AS WEEK3,
SUM(CASE WHEN RISK_START_DATE<= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 28, getdate()) ), 7)
AND RISK_START_DATE+RISK_DURATION >= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 28, getdate()) ), 0)
THEN 1 ELSE 0 END) AS WEEK4,
SUM(CASE WHEN RISK_START_DATE<= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 35, getdate()) ), 7)
AND RISK_START_DATE+RISK_DURATION >= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 35, getdate()) ), 0)
THEN 1 ELSE 0 END) AS WEEK5,
SUM(CASE WHEN RISK_START_DATE<= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 42, getdate()) ), 7)
AND RISK_START_DATE+RISK_DURATION >= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 42, getdate()) ), 0)
THEN 1 ELSE 0 END) AS WEEK6,
SUM(CASE WHEN RISK_START_DATE<= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 49, getdate()) ), 7)
AND RISK_START_DATE+RISK_DURATION >= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 49, getdate()) ), 0)
THEN 1 ELSE 0 END) AS WEEK7,
SUM(CASE WHEN RISK_START_DATE<= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 56, getdate()) ), 7)
AND RISK_START_DATE+RISK_DURATION >= DATEADD(wk, DATEDIFF(wk,0,DATEADD(dd, 56, getdate()) ), 0)
THEN 1 ELSE 0 END) AS WEEK8
from CONSTRUCTION_RISK
~~WHERE DELETE_FLAG=0
and STEP=3
and RISK_LEVEL in (2,3)~~
4. 要求以年为界限,所以需要查询当前年的的1月1日和明年的1月1日。
当前年的1月1日
思路:
① 计算指定日期(以当前日期为例)到SQLServer最小日期(1900-01-01)之间相差多少年:datediff(year, 0, getdate()),结果是相差119年
② 从SQLServer最小日期(1900-01-01)加上距今的年份,就得到了今年的第一天,如下:
SELECT DATEADD(yy,DATEDIFF(yy,0,getdate()),0)
-- 当前年 1月1号
明年的1月1日
思路一:利用明年的今天:DATEADD(yy,1,getdate()
SELECT DATEADD(yy,DATEDIFF(yy,0,DATEADD(yy,1,getdate())),0)
--*繁琐了一些*
思路二:相差年数+1
SELECT DATEADD(yy,DATEDIFF(yy,0,getdate())+1,0)
--明年的1月1日
PS:当前年第一天,当前月第一天,当前日零点,当前年最后一天
SELECT DATEADD(yy,DATEDIFF(yy,0,getdate()),0)
-- 当前年 1月1号
SELECT DATEADD(mm,DATEDIFF(mm,0,getdate()),0)
-- 当前月 1号
SELECT DATEADD(dd,DATEDIFF(dd,0,getdate()),0)
-- 当前日 零点
select DATEADD(ms,-3,dateadd(yy,datediff(yy,0,getdate())+1,0))
--本年的最后一天