游標的使用

2021-05-23 12:33:06 字數 4322 閱讀 2021

游標(cursor)是處理資料的一種方法,為了檢視或者處理結果集中的資料,游標提供了在結果集中一次以行或者多行前進或向後瀏覽資料的能力。我們可以把游標當作乙個指標,它可以指定結果中的任何位置,然後允許使用者對指定位置的資料進行處理。

1.游標的組成

游標包含兩個部分:乙個是游標結果集、乙個是游標位置。

游標結果集:定義該游標得select語句返回的行的集合。游標位置:指向這個結果集某一行的當前指標。

2.游標的分類

游標共有3類

api伺服器游標

transaction-sql游標

api客戶端游標。

其中前兩種游標都是執行在伺服器上的,所以又叫做伺服器游標。

api伺服器游標

api伺服器游標主要應用在服務上,當客戶端的應用程式呼叫api游標函式時,伺服器會對api函式進行處理。使用api函式和方法可以實現如下功能:

開啟乙個連線。

設定定義游標特徵的特性或屬性,api自動將游標影射到每個結果集。

執行乙個或多個transaction-sql語句。

使用api函式或方法提取結果集中的行。

api伺服器游標包含以下四種:靜態游標、動態游標、只進游標、鍵集驅動游標(primary key)

transaction-sql游標

該游標是基於declare cursor 語法,主要用於transaction-sql指令碼、儲存過程以及觸發器中。transaction-sql游標在伺服器處理由客戶端傳送到伺服器的transaction-sql語句。

在儲存過程或觸發器中使用transaction-sql游標的過程為:

宣告transaction-sql變數包含游標返回的資料。為每個結果集列宣告乙個變數。宣告足夠大的變數來儲存列返回的值,並宣告變數的型別為可從資料型別隱式轉換得到的資料型別。

使用declare cursor語句將transaction-sql游標與select語句相關聯。還可以利用declare cursor定義游標的唯讀、只進等特性。 

使用open語句執行select語句填充游標。

使用fetch into語句提取單個行,並將每列中得資料移至指定的變數中。注意:其他transaction-sql語句可以引用那些變數來訪問提取的資料值。transaction-sql游標不支援提取行塊。

使用close語句結束游標的使用。注意:關閉游標以後,該游標還是存在,可以使用open命令開啟繼續使用,只有呼叫deallocate語句才會完全釋放。

客戶端游標

該游標將使用預設結果集把整個結果集快取記憶體在客戶端上,所有的游標操作都在客戶端的快取記憶體中進行。注意:客戶端游標只支援只進和靜態游標。不支援其他游標。

3.游標的生命週期

游標的生命週期包含有五個階段:宣告游標、開啟游標、讀取游標資料、關閉游標、釋放游標。

宣告游標是為游標指定獲取資料時所使用的select語句,宣告游標並不會檢索任何資料,它只是為游標指明了相應的select 語句。

declare 游標名稱 cursor 引數

宣告游標的引數

local與global:local表示游標的作用於僅僅限於其所在的儲存過程、觸發器以及批處理中、執行完畢以後游標自動釋放。global表示的是該游標作用域是整個會話層。由連線執行的任何儲存過程、批處理等都可以引用該游標名稱,僅在斷開連線時隱性釋放。

forward_only與scroll:前者表示為只進游標,後者表示為可以隨意定位。預設為前者。

static、keyset與dynamic: 第乙個表示定義乙個游標,其資料存放到乙個臨時表內,對游標的所有請求都從臨時表中應答,因此,對該游標進行提取操作時返回的資料不反映對基表所作的修改,並且該游標不允許修改。keyset表示的是,當游標開啟時,鍵集驅動游標中行的身份與順序是固定的,並把其放到臨時表中。dynamic表示的是滾動游標時,動態游標反映對結果集內所有資料的更改。

read_only 、scroll_locks與optimistic:第乙個表示的是唯讀游標,第二個表示的是在使用的游標結果集資料上放置鎖,當行讀取到游標中然後對它們進行修改時,資料庫將鎖定這些行,以保證資料的一致性。optimistic的含義是游標將資料讀取以後,如果這些資料被更新了,則通過游標定位進行的更新與刪除操作將不會成功。

標準游標:

declare mycursor cursor 

for select * from master_goods

唯讀游標

declare mycusror cursor

for select * from master_goods

for read only

可更新游標

declare mycusror cursor

for select * from master_goods

for update

開啟游標使用open語句用於開啟transaction-sql伺服器游標,執行open語句的過程中就是按照select語句進行填充資料,開啟游標以後游標位置在第一行。

開啟游標

讀取游標資料:在開啟游標以後,使用fetch語句從transaction-sql伺服器游標中檢索特定的一行。使用fetch操作,可以使游標移動到下乙個記錄,並將游標返回的每個列得資料分別賦值給宣告的本地變數。

fetch [next | prior | first | last | absolute n | relative n ]  from mycursor

into @goodsid,@goodsname

其中:next表示返回結果集中當前行的下一行記錄,如果第一次讀取則返回第一行。預設的讀取選項為next

prior表示返回結果集中當前行的前一行記錄,如果第一次讀取則沒有行返回,並且把游標置於第一行之前。

first表示返回結果集中的第一行,並且將其作為當前行。

last表示返回結果集中的最後一行,並且將其作為當前行。

absolute n 如果n為正數,則返回從游標頭開始的第n行,並且返回行變成新的當前行。如果n為負,則返回從游標末尾開始的第n行,並且返回行為新的當前行,如果n為0,則返回當前行。

relative n 如果n為正數,則返回從當前行開始的第n行,如果n為負,則返回從當前行之前的第n行,如果為0,則返回當前行。

關閉游標呼叫的是close語句,方式如下:

close global mycursor               close mycursor

釋放游標呼叫的是deallocate語句,方法如下:

deallocate glboal mycursor       deallocate mycursor

游標例項:

declare mycusror cursor scroll

for select * from master_goods order by goodsid

open mycursor

fetch next from mycursor

into @goodscode,@goodsname

while(@@fetch_status = 0)

begin

begin

select @goodscode = convert(char(20),@goodscode)

select @goodsname = convert(char(20),@goodsname)

print @goodscode + ':' + @goodsname

endfetch next from mycursor

into @goodscode,@goodsname

endclose mycursor

deallocate mycursor

修改當前游標的資料方法如下:

update master_goods set goodsname = 'yangyang8848' where current of mycursor;

刪除當前游標行資料的方法如下:

delete from master_goods where current of mycursor

select @@cursor_rows 可以得到當前游標中存在的資料行數。注意:此變數為乙個連線上的全域性變數,因此只對應最後一次開啟的游標。

原文:http://www.cnblogs.com/yangyang8848/archive/2009/07/02/1514593.html

游標的使用

declare sql varchar 8000 password varchar 200 密碼 tbname varchar 500 資料庫.dbo.表名,如果不指定 dbo.表名,則匯出資料庫的所有使用者表 filename varchar 1000 匯入 匯出路徑 檔名,如果 tbname引數...

游標的使用

use newsite go object storedprocedure dbo pro cutpoint script date 04 21 2011 10 49 16 set ansi nulls on goset quoted identifier on goalter procedure ...

游標的使用

declare userid varchar 20 將 temp2 值賦給當前游標 declare c getdata cursor forselect userid from temp2 開啟當前游標 並將游標值賦給變數 open c getdata fetch c getdata into us...