数据库查询结果的动态排序

本文探讨了如何在SQL Server中根据存储过程参数实现动态排序查询。通过IF...ELSE、列名作为参数、动态执行SQL语句以及使用用户定义函数(UDF)等方法,解决在不同场景下对查询结果进行排序的问题。文中详细展示了每种方法的实现代码,并分析了其优缺点和适用情况。
摘要由CSDN通过智能技术生成

在公共新闻组中,一个经常出现的问题是“怎样才能根据传递给存储过程的参数返回一个排序的输出?”。在一些高水平专家的帮助之下,我整理出了这个问题的几种解决方案。

一、用IF...ELSE执行预先编写好的查询


  对于大多数人来说,首先想到的做法也许是:通过IF...ELSE语句,执行几个预先编写好的查询中的一个。例如,假设要从Northwind数据库查询得到一个货主(Shipper)的排序列表,发出调用的代码以存储过程参数的形式指定一个列,存储过程根据这个列排序输出结果。Listing 1显示了这种存储过程的一个可能的实现(GetSortedShippers存储过程)。


【Listing 1: 用IF...ELSE执行多个预先编写好的查询中的一个】


CREATE PROC GetSortedShippers

@OrdSeq AS int

AS


IF @OrdSeq = 1

SELECT * FROM Shippers ORDER BY ShipperID

ELSE IF @OrdSeq = 2

SELECT * FROM Shippers ORDER BY CompanyName

ELSE IF @OrdSeq = 3

SELECT * FROM Shippers ORDER BY Phone



  这种方法的优点是代码很简单、很容易理解,SQL Server的查询优化器能够为每一个SELECT查询创建一个查询优化计划,确保代码具有最优的性能。这种方法最主要的缺点是,如果查询的要求发生了改变,你必须修改多个独立的SELECT查询——在这里是三个。


二、用列名字作为参数

  另外一个选择是让查询以参数的形式接收一个列名字。Listing 2显示了修改后的GetSortedShippers存储过程。CASE表达式根据接收到的参数,确定SQL Server在ORDER BY子句中使用哪一个列值。注意,ORDER BY子句中的表达式并未在SELECT清单中出现。在ANSI SQL-92标准中,ORDER BY子句中不允许出现没有在SELECT清单中指定的表达式,但ANSI SQL-99标准允许。SQL Server一直允许这种用法。


【Listing 2:用列名字作为参数,第一次尝试】


CREATE PROC GetSortedShippers

@ColName AS sysname

AS


SELECT *

FROM Shippers

ORDER BY

CASE @ColName

WHEN 'ShipperID' THEN ShipperID

WHEN 'CompanyName' THEN CompanyName

WHEN 'Phone' THEN Phone

ELSE NULL

END



  现在,我们来试一下新的存储过程,以参数的形式指定ShipperID列:


EXEC GetSortedShippers 'ShipperID'



  此时一切正常。但是,当我们视图把CompanyName列作为参数调用存储过程时,它不再有效:


EXEC GetSortedShippers 'CompanyName'



  仔细看一下错误信息:


Server: Msg 245, Level 16, State 1, Procedure GetSortedShippers, Line 5

Syntax error converting the nvarchar value 'Speedy

Express' to a column of data type int.



  它显示出,SQL Server试图把“Speedy Express”(nvarchar数据类型)转换成一个整数值——当然,这个

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值