1. 定义游标定义
游标语句的核心是定义了一个游标标识名,并把游标标识名和一个查询语句关联起来。DECLARE语句用于声明游标,它通过SELECT查询定义游标存储的数据集合。语句格式为:
DECLARE 游标名称 [INSENSITIVE] [SCROLL]
CURSOR FOR select语句
[FOR{READ ONLY|UPDATE[OF 列名字表]}]
参数说明:
INSENSITIVE选项:说明所定义的游标使用SELECT语句查询结果的拷贝,对游标的操作都基于该拷贝进行。因此,这期间对游标基本表的数据修改不能反映到游标中。这种游标也不允许通过它修改基本表的数据。
SCROLL选项:指定该游标可用所有的游标数据定位方法提取数据,游标定位方法包括PRIOR、FIRST、LAST、ABSOLUTE n 和RELATIVE n 选项。
Select语句:为标准的SELECT查询语句,其查询结果为游标的数据集合,构成游标数据集合的一个或多个表称作游标的基表。
在游标声明语句中,有下列条件之一时,系统自动把游标定义为INSENSITIVE游标:
SELECT语句中使用了DISTINCT、UNION、 GROUP BY或HAVING等关键字;
任一个游标基表中不存在唯一索引。
其他
READ ONLY选项:说明定义只读游标。
UPDATE [OF 列名字表]选项:定义游标可修改的列。如果使用OF 列名字表选项,说明只允许修改所指定的列,否则,所有列均可修改。
例如,查询教师名字和所教的课程名,定义游标TCURSOR的语句如下 :
DECLARE TCURSOR CURSOR FOR
SELECT tname, cname
FROM teacher ,couse
WHERE teacher.tno = couse.tno
2. 打开游标
打开游标语句执行游标定义中的查询语句,查询结果存放在游标缓冲区中。并使游标指针指向游标区中的第一个元组,作为游标的缺省访问位置。查询结果的内容取决与查询语句的设置和查询条件。
打开游标的语句格式:
EXEC SQL OPEN 〈游标名〉
如果打开的游标为INSENSITIVE游标,在打开时将产生一个临时表,将定义的游标数据集合从其基表中拷贝过来。
SQL Server中,游标打开后,可以从全局变量@@CURSOR_ROWS中读取游标结果集合中的行数。
例1:打开前面所创建的查询教师姓名和所教课名称的游标。
OPEN tcursor
例2:显示游标结果集合中数据行数
SELECT 数据行数 = @@CURSOR_ROWS

3. 读游标区中的当前元组
读游标区数据语句是读取游标区中当前元组的值,并将各分量依次赋给指定的共享主变量。FETCH语句用于读取游标中的数据,语句格式为:
FETCH [[NEXT|PRIOR|FIRST|LAST| ABSOLUTE n| RELATIVE n]
FROM ] 游标名
[INTO @变量1, @变量2, ….]
其中:
NEXT:说明读取游标中的下一行,第一次对游标实行读取操作时,NEXT返回结果集合中的第一行。
PRIOR、FIRST、LAST、ABSOLUTE n 和RELATIVE n 选项只适用于SCROLL游标。它们分别说明读取游标中的上一行、第一行、最后一行、第n 行和相对于当前位置的第n 行。n 为负值时,ABSOLUTE n 和RELATIVE n 说明读取从游标结果集合中的最后一行或当前行倒数n行的数据。
INTO子句 说明将读取的数据存放到指定的局部变量中,每一个变量的数据类型应与游标所返回的数据类型严格匹配,否则将产生错误。
如果游标区的元组已经读完,那么系统状态变量SQLSTATE的值被设为02000,意为"no tuple found"。
例如,读取tcursor中当前位置后的第二行数据
FETCH RELATIVE 2 FROM tcursor

4. 利用游标修改数据
SQL Server中的 UPDATE语句 和 DELETE语句也支持游标操作,它们可以通过游标修改或删除游标基表中的当前数据行。
UPDATE语句的格式为:
UPDATE table_name
SET 列名=表达式}[,…n]
WHERE CURRENT OF cursor_name
DELETE语句的格式为:
DELETE FROM table_name
WHERE CURRENT OF cursor_name
说明:
CURRENT OF cursor_name:
表示当前游标指针所指的当前行数据。CURRENT OF 只能在UPDATE和DELETE语句中使用。

注意:
o使用游标修改基表数据的前提是声明的游标是可更新的。
o 对相应的数据库对象(游标的基表)有修改和删除权限。

5. 关闭游标
关闭游标后,游标区的数据不可再读。CLOSE语句关闭已打开的游标,之后不能对游标进行读取等操作,但可以使用OPEN语句再次打开该游标。
CLOSE语句的格式为:
CLOSE 游标名
例如:关闭tcursor游标如下描述:
CLOSE tcursor

6 删除游标语句
DEALLOCATE语句删除定义游标的数据结构,删除后不可再用。语句格式:
DEALLOCATE 游标名
例如,删除tcursor游标
DEALLOCATE tcursor

例1,读JS2001班的学生的学号和姓名:
#define MAX 30
EXEC SQL BEGIN DECLARE SECTION;
char TN[12], FU[20]; //定义主变量//
EXEC SQL END DECLARE SECTION;
char tarn1[30][12],tarn2[30][20]; //定义 C 变量//
. . . . . .
EXEC SQL //执行SQL语句,定义游标//
DCLARE Scursor CURSOR FOR //声明游标Scursor//
SELECT sno,sname //查询sno,sname//
FROM student //对student表chax 查询//
WHERE sclass = 'JS2001'; //sclass='JS2001'的班级//
EXEC SQL OPEN Scursor ; //打开游标//
for (i=0; i<MAX; i++)
{ EXEC SQL FETCH FROM Scursor
INTO @TN, @FU; //取到宿主变量//
tarn1= TN; //赋值到C数组变量//
tarn2= FU;
}
....................
EXEC SQL CLOSE Scursor ; //关闭游标//
EXEC SQL DEALLOCATE Scursor ; //删除游标//

例2,定义游标,使结果集包括 pubs 数据库的 authors 表中的所有行和列。因为没指定 SCROLL 选项,FETCH NEXT 是唯一可用的提取选项。
DECLARE authors_cursor CURSOR FOR //声明游标authors_cursor //
SELECT * FROM authors
OPEN authors_cursor //打开游标authors_cursor //
FETCH NEXT FROM authors_cursor //读游标authors_cursor中的一行 //
....................

例3, 定义和使用滚动游标
DECLARE tcursor SCROLL CURSOR FOR
SELECT tname, cname FROM teacher ,couse
WHERE teacher.tno = couse.tno;
OPEN tcursor;
取tcursor中当前位置向下的第二行数据
FETCH RELATIVE 2 FROM tcursor
取tcursor中最后一行数据
FETCH LAST FROM tcursor
取tcursor中当前位置向前的第4行数据
FETCH RELATIVE -4 FROM tcursor

例4 利用 @@FETCH_STATUS 控制一个 WHILE 循环中的游标活动。
DECLARE S_Cursor CURSOR FOR
SELECT sname, sno FROM student
OPEN S_Cursor
FETCH NEXT FROM S_Cursor
WHILE @@FETCH_STATUS = '000000'
BEGIN FETCH NEXT FROM S_Cursor END
CLOSE S_Cursor
DEALLOCATE S_Cursor

例5,职工普调工资,从最低工资调起,每人工资长10%,但工资总额不能超过50万元。当调完某个职工工资后,如果工资总额达到或超过50万元,就不再调了,另外,如果职工全部调了一遍,工资总额还没到50万元,也到此为止。现有职工表emp,定义了一个游标cl,游标的查询语句取出职工号和工资值,并按增序排列。下面是程序代码:
void addsalary()
{ EXEC SQL BEGIN DECLARE SECTION //声明SQL变量//
char empno[8], e_sno,SQLSTATE[6];
float s_sal, e_sal;
EXEC SQL END DECLARE SECTION; //声明SQL变量完//
EXEC SQL DECLARE cl CURSOR FOR //定义游标 cl ,对emp表的eno,sal列可以作任何操作
SELECT eno, sal
FROM emp
ORDER BY sal ASC;
EXEC SQL OPEN cl; //打开游标/
EXEC SQL SELECT SUM(sal) INTO @s_sal FROM emp; //取工资总和到s_sal
while(s_sal < 500000.00)
{
EXEC SQL FETCH FROM cl
INTO @e_sno , @e_sal; //从游标中读出的数据放入e_sno,e_sal变量
If(SQLSTATE='02000') BREAK; //读完记录,退出//
EXEC SQL UPDATE emp
SET sal=sal*1.1 //游标内容更新,将empno=e_sno相应的sal*1.1
WHERE empno=@e_eno;
s_sal = s_sal+ e_sal *0.1; //计算工资总和到s_sal
};
EXEC SQL CLOSE cl; /关闭游标/}

 SQL Server提供两种游标应用接口方法:第一种是符合ANSI标准的SQL游标语句,它们可以实现声明、打开、读取或关闭游标操作,这些语句可用在 Transact_SQL语句或存储过程内;第二种是库函数形式,客户端的DB_Library 或ODBC应用程序可以调用这些函数。
 游标语句增强了Transact_SQL对集合数据的处理能力,在SQL Server中,通过游标还可以修改或删除基表中的数据。

7,使用游标时应注意的问题:
(1) 尽管使用游标比较灵活,可以实现对数据集中单行数据的直接操作,但游标会在下面几个方面影响系统的性能:
-使用游标会导致页锁与表锁的增加
-导致网络通信量的增加
-增加了服务器处理相应指令的额外开销
(2) 使用游标时的优化问题:
-明确指出游标的用途:for read only或for update
-在for update后指定被修改的列

转载于:https://www.cnblogs.com/shangguanjunzhi/p/3392529.html

SQL SERVER游标浅析相关推荐

  1. 游标sql server_学习SQL:SQL Server游标

    游标sql server SQL Server cursors are one common topic on the Internet. You'll find different opinions ...

  2. 游标sql server_使用SQL Server游标–优点和缺点

    游标sql server 介绍 (Intro) In relational databases, operations are made on a set of rows. For example, ...

  3. MS SQL Server 游标及实例(三)

    Sql server 中游标具体实例介绍:   表一 OriginSalary 表二 AddSalary 现在有2张表,一张是OriginSalary表--工资表,有三个字段0_ID 员工号(NVAR ...

  4. 什么是Sql Server游标

    什么是Sql Sever游标 游标的概述 在数据库中,游标是一个十分重要的概念.游标提供了一种对从表中检索出的数据进行操作的灵活手段,就本质而言,游标实际上是一种能从包括多条数据记录的结果集中每次提取 ...

  5. SQL server 游标(只进游标)讲解

    游标概念: SQL的游标是一种临时的数据库对象,既可以存放储存在数据库表中数据行的副本,也可以指向储存在数据库中的数据行的指针,游标提供了在逐行的基础上操作表中数据的方法. 游标的作用: 1.定位到结 ...

  6. SQL Server 游标的使用示例

    Ø  简介 本文主要记录 MSSQL 中的游标使用示例,在有必要时方便借鉴查阅.游标一般定义在某段功能性的 SQL 语句中,或者存储过程中.之所以选择用它,是因为有时候无法使用简单的 SQL 语句满足 ...

  7. SQL Server游标的使用【转】

    游标是邪恶的! 在关系数据库中,我们对于查询的思考是面向集合的.而游标打破了这一规则,游标使得我们思考方式变为逐行进行.对于类C的开发人员来着,这样的思考方式会更加舒服. 正常面向集合的思维方式是: ...

  8. sql server 游标的使用

     1 -- zhxia  2 DECLARE @username VARCHAR(20),@flag BIT,@ncount int  3 DECLARE mycursor CURSOR FOR -- ...

  9. SQL Server游标的使用

    转自+ http://www.cnblogs.com/moss_tan_jun/archive/2011/11/26/2263988.html 游标是邪恶的! 在关系数据库中,我们对于查询的思考是面向 ...

最新文章

  1. 51nod 1038 X^A Mod P( N 次剩余)
  2. MySQL的SQL语句如何优化?
  3. 003_onreadystatechange事件
  4. c 正则表达式替换html,正则表达式替换html元素属性的方法
  5. ScheduledExecutorService
  6. MySql里的My是指谁?
  7. 在linux下利用ls命令进行模糊查找
  8. php 0改成百 千_【面试题】小数转换为人民币大写形式,PHP实现。
  9. cocos creator 判断双击_Creator | 编辑器中可操作顶点的多边形遮罩
  10. java基础----Serializable的使用---- http://www.cnblogs.com/huhx/p/serializable.html
  11. BeamSearch的原理和实现
  12. 【网络原理】期末复习笔记 第一章 概述
  13. BZOJ3669[NOI2014] 魔法森林
  14. vscode调试时几个常用参数的含义和设置总结
  15. matlab函数sinh,matlab sinh 使用方法
  16. 逻辑回归之ROC曲线的绘制
  17. oracle和timesten整合,Timesten与Oracle SQL执行时间对比
  18. Mysql查询排名10到20名
  19. kendalltau肯德尔和谐系数
  20. 64位:浪来滔滔江水永不休

热门文章

  1. 英美安全机构称俄罗斯正在暴力攻击全球数百家组织机构
  2. 美国太空部队加入美国情报系统,以确保太空的安全
  3. XP远程桌面连接强制登录
  4. Jupyter notebook实现远程登陆
  5. [2019.3.21]洛谷P3640 [APIO2013]出题人
  6. 万亿安防市场前景可期 未来四大发展趋势分析
  7. 饿了么合并百度外卖,ThinkSNS:产品上线要趁早
  8. EJB3.0高速入门项目开发步骤
  9. dubbo学习--导入eclipse异常Unbound classpath container(2)
  10. AngularJS Filters