sql server 流程控制

CASE...WHEN...

简单表达式:

select top 4 
    case ZhiYeID
    when 1 then '老板'
    when 2 then '经理'
    when 3 then '搬砖'
    else '打杂'
    end as '职位',ZhiYeID
    from  ZhiWei order by ZhiYeID

每个ZhiYeID都与每个when逐行匹配后面的值比较,匹配则取该when后then的值,否则取下一行when后面的值,都不匹配则取else后面的值。

因为CASE简单表达式的值只局限在一列(字段field)当中,所以THEN后面的值数据类型必须相同,或者兼容,否则就会报错。

CASE搜索表达式把字段名写在when后面

CASE搜索表达式提供了更强大的功能,CASE搜索表达式不仅可以使用更复杂的逻辑表达式,并且还能根据多列中的数据确定所显示列的值。

公司员工病假休假不得超过30小时,取得所有男性员工的ID,如果员工病假或者是休假任意一项超过了30个小时,标记为"超出假期",两项都不超过30个小时的,标记为"还可请假"
SELECT EmployeeID,
      CASE 
      WHEN VacationHours>30 AND Gender='M' THEN '超出假期'
      WHEN SickLeaveHours>30 AND Gender='M' THEN '超出假期'
      ELSE '还可请假'
      END AS "请假情况"
  FROM [AdventureWorks].[HumanResources].[Employee]

因为CASE表达式是基于列的,一个CASE表达式只能返回一个值,所以基于多少个值排序,则需要多少个CASE表达式

比如:我想查看省份ID为8和9的员工的地址,当省份ID为9时,按照AddressID降序排列,当省份ID为8时,按照AddressID升序排列

SELECT [AddressID]
      ,[AddressLine1]
      ,[City]
      ,[StateProvinceID]
      FROM [AdventureWorks].[Person].[Address]
WHERE StateProvinceID=9 OR StateProvinceID=8
ORDER BY  
         CASE WHEN StateProvinceID=9 THEN AddressID END DESC,
         CASE WHEN StateProvinceID=8 THEN AddressID END

流程控制

流程控制语句(if else)只能在单个批处理段(Batch),用户自定义函数和存储过程中使用。不能跨多个批处理段或者用户自定义函数和存储过程。

一个批处理段是由一个或者多个语句组成的一个批处理,之所以叫批处理是因为所有语句一次性被提交到一个SQL实例。在这个批处理范围内,局部变量是互相可见的。

而想让多个语句分多次提交到SQL实例,则需要使用GO关键字。GO关键字本身并不是一个SQL语句,GO关键字可以看作是一个批处理结束的标识符,当遇到GO关键字时,当前GO之前的语句会作为一个批处理直接传到SQL实例执行。所以不在同一个批处理内局部变量不可见,也不可对跨批处理的语句使用流程控制语句.

被中断的批处理
DECLARE @a int
select @a=2
go
if @a=2
	select 2
	else select 0

在T-SQL中,与流程控制语句相关的关键字有8个:

BEGIN...END BREAK
GOTO CONTINUE
IF...ELSE WHILE
RETURN WAITFOR

BEGIN…END关键字

BEGIN…END关键字也是流程控制语句需要用到的最基本关键字,用于将多个语句划分成逻辑上的一部分。其实可以直接理解成类C语言中的花括号(“{}"“)

WHILE/BREAK/CONTINUE关键字

在T-SQL的流程控制语句中,循环语句只有WHILE循环,并没有传统高级语言的FOR和SWITCH循环。WHILE除了被用于流程控制语句的循环之外,还经常被用于游标之中。

WHILE关键字和高级语言中的WHILE关键字几乎完全一样。WHILE循环中可以利用BREAK和CONTINUE关键字对循环进行控制。

CONTINUE关键字用于结束本次循环,直接开始下一次循环。

BREAK关键字用于直接跳出WHILE循环语句。

这里值得注意的是,当WHILE循环嵌套时,CONTINUE关键字和BREAK关键字只会作用于它们所处的WHILE循环之内,不会对外部WHILE循环产生作用。

IF..ELSE关键字

IF..ELSE关键字实现了非此既彼的逻辑。和高级语言中的IF..ELSE具有完全一样的使用方法。
if或else后面的语句较多最好用begin end包起来。

要注意的是IF经常会和EXISTS关键字相结合来查看数据表中指定的数据是否存在。

GOTO关键字

GOTO关键字因为能打乱程序的整个流程而在高级语言中臭名卓著。GOTO关键字的使用非常简单,定义一个跳转标签,只要GOTO 标签名就可以。如果说一定要使用GOTO关键字的话,最佳实践是只使用在错误处理上,比如:

if (@@error<>0)
    goto error
error:select 'ERROR DESCRIPTION'

RETURN关键字

Return是最简单有效直接无条件告诉服务器跳出某个批处理段(Batch),用户自定义函数和存储过程的方式。

begin 
select '123'
RETURN 
select '234'
END
报错并继续执行
begin 
print '123'
RAISERROR ('报错了!',2,1)
print '234'
END

WAITFOR关键字允许指定语句在特定时间或是推迟特定时间执行。

推迟等待和在特定时间执行的语法分别是WAITFOR DELAY :需要延时的时间(00:00:03(时分秒)),WAITFOR TIME :需要执行程序的精确时间。

waitfor只执行一次,触发器可执行多次

10小时候搞优惠活动,1000的货物价格调为900,20小时后调回原价1000:
declare @starttime Datetime @endtime Datetime
set @starttime=cast(getdate()+'10:00:00' as datetime)
set @endtime=cast(getdate()+'20:00:00' as datetime)
waitfor time @starttime
begin
update huoWu set jiaGe=900 where jiaGe=1000
end
waitfor time @endtime
begin
update huoWu set jiaGe=1000 where jiaGe=900
end
posted @ 2020-10-30 10:22  Neroi  阅读(171)  评论(0编辑  收藏  举报