技术开发 频道

微软SQL Server支持的三种游标实现

  【IT168 技术】在数据库中,游标是一个十分重要的概念。游标提供了一种对从表中检索出的数据进行操作的灵活手段,就本质而言,游标实际上是一种能从包括多条数据记录的结果集中每次提取一条记录的机制。Microsoft SQL Server 支持三种游标实现:

  Transact-SQL 游标

  基于 DECLARE CURSOR 语法,主要用于 Transact-SQL 脚本、存储过程和触发器。Transact-SQL 游标在服务器上实现并由从客户端发送到服务器的 Transact-SQL 语句管理。它们还可能包含在批处理、存储过程或触发器中。

  应用程序编程接口 (API) 服务器游标

  支持 OLE DB 和 ODBC 中的 API 游标函数。API 服务器游标在服务器上实现。每次客户端应用程序调用 API 游标函数时,SQL Server Native Client OLE DB 访问接口或 ODBC 驱动程序会把请求传输到服务器,以便对 API 服务器游标进行操作。

  客户端游标

  由 SQL Server Native Client ODBC 驱动程序和实现 ADO API 的 DLL 在内部实现。客户端游标通过在客户端高速缓存所有结果集行来实现。每次客户端应用程序调用 API 游标函数时,SQL Server Native Client ODBC 驱动程序或 ADO DLL 会对客户端上高速缓存的结果集行执行游标操作。

  由于 Transact-SQL 游标和 API 服务器游标都在服务器上实现,所以它们统称为服务器游标。

  不要混合使用这些不同类型的游标。如果从一个应用程序中执行 DECLARE CURSOR 和 OPEN 语句,请首先将 API 游标属性设置为默认值。否则就会要求 SQL Server 将 API 游标映射到 Transact-SQL 游标。例如,不要将 ODBC 属性设置为需要将由键集驱动的游标映射到结果集,然后使用该语句句柄执行 DECLARE CURSOR 和 OPEN 以调用 INSENSITIVE 游标。

  服务器游标的一个潜在缺点是它们目前并不支持所有的 Transact-SQL 语句。服务器游标不支持生成多个结果集的 Transact-SQL 语句,因此,当应用程序执行包含多个 SELECT 语句的存储过程或批处理时,不能使用服务器游标。服务器游标也不支持包含 COMPUTE、COMPUTE BY、FOR BROWSE 或 INTO 关键字的 SQL 语句。

  服务器游标与默认结果集的比较

  使用游标不如使用默认结果集的效率高。在默认结果集中,从客户端发送到服务器的唯一数据包是包含待执行语句的数据包。而在使用服务器游标时,每个 FETCH 语句都必须从客户端发送到服务器,然后在服务器上分析并编译为执行计划。

  如果某个 Transact-SQL 语句将返回一个相对较小的结果集,可以高速缓存在客户端应用程序可用的内存中,而且您知道必须在执行该语句之前检索整个结果集,那么请使用默认结果集。只有在需要进行游标操作以支持应用程序的功能,或者可能只需检索结果集的一部分时,才应使用服务器游标。

  服务器游标与客户端游标的比较

  用服务器游标代替客户端游标有以下几个优点:

  1.性能

  在访问游标中的部分数据时(这在许多浏览应用程序中很常见),使用服务器游标能够提供非常好的的性能,因为只通过网络发送提取的数据。客户端游标则将整个结果集高速缓存在客户端。

  2.其他游标类型

  如果 SQL Server Native Client ODBC 驱动程序只使用客户端游标,它可能只支持只进游标和静态游标。通过使用 API 服务器游标,该驱动程序也可以支持由键集驱动的游标和动态游标。SQL Server 还支持只有通过服务器游标才能获得的所有游标并发属性。客户端游标仅限于它们所支持的功能。

  3.更精确的定位更新

  服务器游标直接支持定位操作,例如 ODBC 的 SQLSetPos 函数,或带有 WHERE CURRENT OF 子句的 UPDATE 和 DELETE 语句。另一方面,通过生成 Transact-SQL 搜索的 UPDATE 语句,客户端游标可以模拟定位游标更新,如果有多个行满足 UPDATE 语句的 WHERE 子句的条件,这将导致意外更新。

  4.内存使用

  在使用服务器游标时,客户端无需高速缓存大量数据或维护游标位置的信息,因为这些工作由服务器完成。

  5.多个活动语句

  使用服务器游标时,结果不会存留在游标操作之间的连接上。这就允许同时拥有多个基于游标的活动语句。

  除了静态游标或不敏感游标外,所有服务器游标的操作都取决于基础表的架构。声明游标后对这些表的架构进行任何更改都将导致该游标的后续操作发生错误。

0
相关文章