对查询出来的结果集进行读取
类似于循环遍历数组,可定位
缺点:存放到TempDB里(临时表),内存有限。
适合:表数据少的时候
分类:静态,动态,只进,键值驱动游标
静态:类似于快照,支持滚动(向前向后读取都可以),数据库发生改变,结果集不变(消耗资源少)
动态:支持前后滚动,前后滚动时,结果集是重新获取一边,所以,顺序,数据都会发生改变。对数据库的改变可以通过游标可见。api函数或t-sql where current of 子句通过游标进行更新。游标外部所作的更新,直到提交才可见。(消耗资源多,不推荐)
只进:只能向前读取,不支持滚动,未读取的对数据库所做的更新在提取时是可见的,读取了就不能回头更新了。(消耗资源最少)
生命周期:声明,打开,读取,关闭,释放
下面是只进游标:
declare u_test cursor local--声明游标,,,global全局游标 for --SQL select * from test where age=8 open u_test--打开游标 --声明变量 declare @u_test cursor,@id int,@uName varchar(50),@age int,@datetime varchar set @u_test = u_test --读取单行数值,next向下,prior向上,first第一个,last最后一个 --absolute n绝对位置,relative n从当前位置开始第n个 fetch next from u_test into @id,@uName,@age,@datetime --循环,状态不为0 while @@FETCH_STATUS=0 begin print convert(varchar,@id)+','+@uName+','+convert(varchar,@age); if @id=17--单查询结果集里没id=17,哪怕数据库里有,也不会执行 update test set Tname='li',age=8 where id=19 if @id=19 update test set Tname='lio',age=8 where id=17 fetch next from u_test into @id,@uName,@age,@datetime--下一条 end close u_test--关闭游标 deallocate u_test--释放游标 go
结果:
这里的更改我使用了触发器,所以可以看出他的过程,运行到id=17时,进行更改,id=19就变了,后显示出来,运行到id=19时,虽然也对数据库进行了更改,到id=17,以及读出来了
静态游标
declare u_test_static cursor static local--声明游标,,,global全局游标 for --SQL select * from test where age=8 open u_test_static--打开游标 --声明变量 declare @u_test cursor,@id int,@uName varchar(50),@age int,@datetime varchar set @u_test = u_test_static --读取单行数值,next向下,prior向上,first第一个,last最后一个 --absolute n绝对位置,relative n从当前位置开始第n个 fetch next from u_test_static into @id,@uName,@age,@datetime --循环,状态不为0 while @@FETCH_STATUS=0 begin print convert(varchar,@id)+','+@uName+','+convert(varchar,@age); if @id=17--单查询结果集里没id=17,哪怕数据库里有,也不会执行 update test set Tname='111',age=8 where id=19 if @id=19 update test set Tname='2222',age=8 where id=17 if @id=20 fetch absolute 2 from u_test_static into @id,@uName,@age,@datetime fetch next from u_test_static into @id,@uName,@age,@datetime--下一条 end close u_test_static--关闭游标 deallocate u_test_static--释放游标 go
静态游标,虽然修改了数据库的信息,但当我后退去读取id=17时,那一行在静态游标的结果集没变
动态游标:
declare u_test_dynamic cursor dynamic local--声明游标,,,global全局游标 for --SQL select * from test where age=8 open u_test_dynamic--打开游标 --声明变量 declare @u_test cursor,@id int,@uName varchar(50),@age int,@datetime varchar set @u_test = u_test_dynamic --读取单行数值,next向下,prior向上,first第一个,last最后一个 --absolute n绝对位置,relative n从当前位置开始第n个 fetch next from u_test_dynamic into @id,@uName,@age,@datetime --循环,状态不为0 while @@FETCH_STATUS=0 begin print convert(varchar,@id)+','+@uName+','+convert(varchar,@age); if @id=17--单查询结果集里没id=17,哪怕数据库里有,也不会执行 update test set Tname='abc',age=8 where id=19 if @id=19 update test set Tname='efg',age=8 where id=17 if @id=20 --提取类型 Absolute 不能与动态游标一起使用。 fetch first from @u_test into @id,@uName,@age,@datetime fetch next from u_test_dynamic into @id,@uName,@age,@datetime--下一条 end close u_test_dynamic--关闭游标 deallocate u_test_dynamic--释放游标 go
结果集,可前后滚动,可即时获取
本文来自博客园,作者:阿霖找BUG,转载请注明原文链接:https://www.cnblogs.com/lin-07/p/17336252.html