「時我第一次呼叫功能它返回第一staff_id = 1;當我第二次呼叫功能它返回第一staff_id = 2;當我n個時間呼叫功能它返回第一staff_id = N;且之後,循環再次重複「
程序思維通常是一種代碼味道。關係數據庫用於處理數據集。但是,到底什麼時候,讓我們享受一些午餐時間的樂趣吧:
我們需要一個包,因爲包變量允許我們維護函數調用的狀態。 (有這樣做的其他方式,如上下文的命名空間,但一個包是容易實現的。)
create or replace package pkg_test is
function get_staff_id (p_dept_id number) return number;
end pkg_test ;
/
create or replace package body pkg_test is
-- variables to maintain state across function calls
ids_nt dbms_utility.number_array;
idx number := 0;
last_dept_id number := 0;
function get_staff_id (p_dept_id number) return number
is
return_value number;
begin
if idx = 0
or last_dept_id != p_dept_id
then
select staff_id
bulk collect into ids_nt
from staff
where dept_id = p_dept_id;
last_dept_id := p_dept_id;
idx := 0;
end if;
idx := idx + 1;
return_value := ids_nt(idx);
if idx = ids_nt.count() then
idx := 0;
end if;
return return_value;
end get_staff_id ;
end pkg_test ;
/
注意
- 保持這樣的全局狀態一般不考慮好實踐。它在這裏工作,但在更復雜的過程中,狀態很容易被我們不期望的調用改變。
- 狀態保持在會話級別。兩個單獨的會話將獲得兩組數據,而不是一個交錯組。所以對於使用連接池的應用程序來說這不是一個好的實現。
來源
2017-05-26 11:32:14
APC
這不是很清楚。你有一張表,但你想要一個函數來對這張表進行查詢,但是在一個雙重查詢中?你不能簡單地查詢你的表嗎?這個函數的返回類型應該是什麼。此外,請發佈數據作爲格式化文本,[不截圖](http://meta.stackoverflow.com/questions/285551/why-may-i-not-upload-images-of-code-on-so-when-問一個問題/ 285557#285557) – Aleksej
那麼你想從一個你不從純SQL獲得的函數中獲得什麼好處?從dept_id = 443'的staff中選擇staff_id? – APC
當我第一次調用函數時,首先返回staff_id = 1; 當我第二次調用函數時,它首先返回staff_id = 2; 當我n次調用函數時,首先返回staff_id = n; 然後循環再次重複 – Tiko