CASE表达式是一个标量表达式,它基于条件逻辑来返回一个值。注意,CASE是一个表达式,而不是一条语句;也就是会所,不能用它来控制活动的流程,也不能根据条件逻辑来做某些处理。相反,它只是根据条件逻辑来返回某个值。因为CASE是一个标量表达式,所以它可以支持任何标量表达式(如SELECT、WHERE、HAVING,以及ORDER BY子句)、CHECK约束,等等。
CASE表达式有两种格式:简单表达式和搜索表达式。CASE简单格式将一个值(或一个标量表达式)与一组可能的取值进行比较,并返回第一个匹配的结果。如果列表中没有值等于测试值,CASE表达式就返回其ELSE子句(如果存在)中列出的值。如果CASE表达式中没有ELSE子句,则默认将其视为ELSE NULL。
例如,以下对Production.Products表的查询就在SELECT子句中使用了CASE表达式,以生成用于描述categoryid列取值的信息:
3 WHEN1THEN'Beverages'
4 WHEN2THEN'Condiments'
5 WHEN3THEN'Confections'
6 WHEN4THEN'Dairy Products'
7 WHEN5THEN'Grains/Cereals'
8 WHEN6THEN'Meat/Poultry'
9 WHEN7THEN'Produce'
10 WHEN8THEN'Seafood'
11 ELSE'Unknown Category'
12 ENDAS categoryname
13 FROM Production.Products;
该查询生成以下输出:
这个查询是使用CASE表达式的一个简单例子。除非商品种类的数量非常少,而且也是静态的,否则最好的设计选择可能是应该在另一个单独的表中来维护商品种类;当需要获取种类描述时,把那个表和Products进行连结(join)操作。
作为CASE简单表达式的另一个演示,以下对Sales.OrderValues视图的查询先根据val的逻辑顺序生成3个组,再把组的编号翻译成组的描述信息(Low、Medium,以及High):
3 WHEN1THEN'Low'
4 WHEN2THEN'Medium'
5 WHEN3THEN'High'
6 ELSE'Unknown'
7 ENDAS titledesc
8 FROM Sales.OrderValues
9 ORDERBY val;
该查询会输出以下输出:
CASE简单表达式只有一个测试值(或表达式),它紧跟在CASE关键字后面,与WHEN子句中的一组可能值进行比较。CASE搜索表达式要更灵活些,它可以在WHEN子句中指定谓词或逻辑表达式,而不限于只进行相等性比较。CASE搜索表达式返回结果为TRUE的第一个WHEN逻辑表达式所关联的THEN子句中指定的值。如果没有任何WHEN表达式结果为TRUE,CASE表达式就返回ELSE子句中出现的值(如果没有指定ELSE子句,则返回NULL)。例如,以下查询根据商品的价格是否小于1000.00、在1000.00到3000.00之间、或者大于3000.00而生成相应的价格描述:
3 WHEN val <1000.00THEN'Less then 1000'
4 WHEN val BETWEEN1000.00AND3000.00THEN'Between 1000 and 3000'
5 WHEN val >3000.00THEN'More than 3000'
6 ELSE'Unknown'
7 ENDAS valuecategory
8 FROM Sales.OrderValues;
该查询会生成以下输出:
可以看到,每个CASE简单表达式都可以转换成CASE搜索表达式,但并非所有情况都有必要使用CASE搜索表达式。