T-sql 游标
游標簡介:
???? Sql游標提供了一種循環結果集的機制,它對數據集中的數據進行逐行讀取,可以實現不易用select語句語法輕易地表達復雜計算。
???? 通過sql語言從數據庫中檢索數據口,然后把結果放到內存的一塊區域中.往往這個結果講包含多條數據,這也是游標產生了一個不可避免的弊端對系統資源占用相對較大。
游標的使用過程:
1.聲明游標
2.打開游標
3.從游標中重復(讀取)行,有選擇的修改或者刪除
4.關閉游標
5.當不再需要游標時,釋放游標
?
聲明一個游標
?DECLARE 游標名 [ INSENSITIVE ] [ SCROLL ] CURSOR
FOR sql-statement
例:Declare Mycursor
?? For select * from tb_name
打開游標
OPEN?MyCursor
游標的操作
?FETCH
?? ?? ????? [ NEXT | PRIOR | FIRST | LAST]
FROM
{ 游標名 | @游標變量名 } [ INTO @變量名 [,…] ]
一.?? 可滾動游標
?Next?????? 當前行的下一行
?Prior?????? 當前行的前一行
?First?????? 第一行
?Last??????? 最后一行
?Absolute n?? n>0,定位到從開始的第n行
?????????????????? n=0 沒有返回行
??????????????????? n<0 定位到末尾前的第n行
?Relative n?? n<-1 定位到當前行之前的第n行
????????????????? n=-1 通Prior關鍵字相同
????? ??????????? n=0 定位到當前行 [重讀]
????????????????? n=1 同Next關鍵字相同
???????????????? N>1定位到當前行之后的第n行
?
Code
---聲明游標
DECLARE?@MyVariable?CURSOR
DECLARE?@LastName?varchar(50),?@FirstName?varchar(50)
select?@LastName,@FirstName
DECLARE?MyCursor?CURSOR?FOR
SELECT?top?10?keyid,keyname?FROM?test1
open?MyCursor?
while?@@Fetch_status=0
begin
FETCH???next???FROM???MyCursor?INTO?@LastName,?@FirstName
select?@LastName,@FirstName
end
close?mycursor
deallocate?mycursor
--刪除語句
declare?test??cursor?for
select?top?10?ID?from?test1?order?by?ID??asc
declare?@ID?nvarchar(10)
open?test
fetch?next?from?test?into?@ID
while?@@fetch_status=0
begin
????delete?from??test1????where?ID=@ID
????fetch?next?from?test?into?@ID
end
close?test
deallocate?test
--更新UPDATE語句
declare?test??cursor?for
select?top?50?ID?from?test1?order?by?ID?
declare?@ID?nvarchar(10),@ID2?int
open?test
set?@ID2=0
fetch?next?from?test?into?@ID
while?@@fetch_status=0
begin
SET?@ID2?=?@ID2?+?1
????update?test1
????set?keyname=Cast(@ID2?as?nvarchar(10))
????where?ID=@ID
????fetch?next?from?test?into?@ID
end
close?test
deallocate?test
go
每執行一個FETCH操作之后,通常都要查看一下全局變量@@FETCH_STATUS中的狀態值,以此判斷FETCH操作是否成功。該變量有三種狀態值:
· 0 表示成功執行FETCH語句。
· -1 表示FETCH語句失敗,例如移動行指針使其超出了結果集。
· -2 表示被提取的行不存在。
由于@@FETCH_STATU是全局變量,在一個連接上的所有游標都可能影響該變量的值。因此,在執行一條FETCH語句后,必須在對另一游標執行另一FETCH 語句之前測試該變量的值才能作出正確的判斷。
?
?
?
Code??USE?master
????GO
CREATE?PROCEDURE?sp_BuildIndexes
AS
DECLARE?@TableName?sysname,?@msg?varchar(100),?@cmd?varchar(100)
DECLARE?table_cur?CURSOR?FOR
SELECT?name?FROM?sysobjects?WHERE?type=’u’
OPEN?table_cur
FETCH?NEXT?FROM?table_cur?INTO?@TableName
WHILE?@@fetch_status?=?0
BEGIN
IF?@@fetch_status?=?-2
CONTINUE
SELECT?@msg?=?“Building?indexes?for?table”+@TableName+”…”
PRINT?@msg
SELECT?@cmd?=?“DBCC?DBREINDEX?(‘”+@TableName+”')”
EXEC?(@cmd)
PRINT?“?“
FETCH?NEXT?FROM?table_cur?INTO?@TableName
END
DEALLOCATE?table_cur
GO
下面的腳本將為PUBS數據庫執行sp_BuildIndexes
USE?pubs
GO
EXEC?ap_BuildIndexes
Code
use?pubs
go
declare?@int?int
declare?mycursor?scroll?cursor
for?select??job_id??from?jobs
open?mycursor
Fetch?Next?From?mycursor??into?@int?--之前缺少這句?,
---@@Fetch_status?所得到的數值總是-1
while?@@Fetch_status?=?0
begin
print?@int
?FETCH?Next?FROM?mycursor?into?@int?
end
close?mycursor
deallocate?mycursor
轉載于:https://www.cnblogs.com/rhythmK/archive/2009/08/10/1542754.html
總結
- 上一篇: 解决StreamReader读取中文出现
- 下一篇: POJ 1088----滑雪(DP)