CURSOR游标的使用
结构
DECLARE Emp_Cursor CURSOR FOR
SELECT EmpID, EmpName FROM Employee
OPEN Emp_Cursor
FETCH NEXT FROM Emp_Cursor
WHILE @@FETCH_STATUS = 0
BEGIN
--DO SOMETHING WITH CURSOR
FETCH NEXT FROM Emp_Cursor
END
CLOSE Emp_Cursor
DEALLOCATE Emp_Cursor
步骤
声明游标:
DECLARE [游标名称] CURSOR FOR [SELECT语句]
,FOR后面的查询结果就是游标的内容,后续将对其逐行提取
打开游标:
OPEN [游标名称]
提取一行:
FETCH NEXT FROM [游标名称]
,提取第一步的查询结果,每执行一次FETCH NEXT依次提取一行
判断状态:
执行一次FETCH NEXT之后,通过系统变量@@FETCH_STATUS
指示操作结果:提取成功返回0,失败返回-1(如已到达最后一行)
@@FETCH_STATUS状态
返回值 | 说明 |
---|---|
0 | FETCH 语句成功。 |
-1 | FETCH 语句失败或行不在结果集中。 |
-2 | 提取的行不存在。 |
-9 | 游标未执行提取操作。 |
关闭游标:
CLOSE [游标名称]
释放游标:
DEALLOCATE [游标名称]
应用方法
DO SOMETHING WITH CURSOR
一般会将提取到的值赋给变量,用于执行相关任务:
先声明变量名及类型,然后使用FETCH NEXT FROM Emp_Cursor INTO @A,@B
,即可将游标内容赋给变量@A和@B。
此赋值操作是按列依次赋值给变量的,即第一列的值赋给@A,第二列的值赋给@B。
DECLARE Emp_Cursor CURSOR FOR
SELECT EmpID, EmpName FROM Employee
OPEN Emp_Cursor
DECLARE @A INT
DECLARE @B VARCHAR(20)
FETCH NEXT FROM Emp_Cursor INTO @A,@B
WHILE @@FETCH_STATUS = 0
BEGIN
--DO SOMETHING WITH @A,@B
FETCH NEXT FROM Emp_Cursor INTO @A,@B
END
CLOSE Emp_Cursor
DEALLOCATE Emp_Cursor
在触发器、存储过程中使用游标
游标常常与触发器或者存储过程一起使用。
即在触发器、存储过程中利用游标更新变量,达到批量处理的效果。
游标嵌套
即在游标遍历过程中,将每次遍历得到的变量作为条件查询新的集合,再为新集合创建新的游标对其进行深一层的遍历。
该用法常用于查询有层级结构的数据。
注意事项
- WHILE循环开始前,执行一次FETCH NEXT;循环体结束前,也需要执行一次FETCH NEXT,否则@@FETCH_STATUS并没有更新。
- FETCH NEXT已到达最后一行,后续@@FETCH_STATUS会返回-1,但游标仍然是最后一行数据。
- 游标结束前,必须执行CLOSE和DEALLOCATE命令,以关闭和释放游标,否则下次创建游标时出现游标已存在错误。