存儲過程的 概念:
存儲過程:就是一塊PLSQL語句包裝起來,起個名稱
語法上:相當(dāng)于plsql語句戴個帽子。
相對而言:單純plsql可以認為是匿名程序。
存儲作用:
1,在開發(fā)程序中,為了一個特定的業(yè)務(wù)功能,會向數(shù)據(jù)庫進行多次連接關(guān)閉(連接和關(guān)閉是很耗費資源)。這種就需要對數(shù)據(jù)庫進行多次I/O讀寫,性能比較低。如果把這些業(yè)務(wù)放到PLSQL中,在應(yīng)用程序中只需要調(diào)用PLSQL就可以做到連接關(guān)閉一次數(shù)據(jù)庫就可以實現(xiàn)我們的業(yè)務(wù),可以大大提高效率.
2,?ORACLE官方給的建議:能夠讓數(shù)據(jù)庫操作的不要放在程序中。在數(shù)據(jù)庫中實現(xiàn)基本上不會出現(xiàn)錯誤,在程序中操作可以會存在錯誤.(如果在數(shù)據(jù)庫中操作數(shù)據(jù),可以有一定的日志恢復(fù)等功能.)
提示:
l?plsql是存儲過程的基礎(chǔ)。
l?java是不能直接調(diào)用plsql的,但可以通過存儲過程這些對象來調(diào)用。
存儲過程的語法:
create or replace PROCEDURE 過程名(參數(shù)名) AS/IS plsql子程序體
根據(jù)參數(shù)的類型,我們將其分為3類講解:
l不帶參數(shù)的
l帶輸入?yún)?shù)的
l帶輸入輸出參數(shù)的。
<1>無參存儲:
創(chuàng)建存儲:建議使用PROCEDURE這個窗口
create or replace procedure p_hello IS
begin?
?dbms_output.put('b');?--寫入buffer但不輸出
dbms_output.new_line;?--回車(換行),輸出?????????????????????????????
?dbms_output.put_line('hello world!');?--輸出并換行
end p_hello
測試存儲:

調(diào)用方法:
如何調(diào)用執(zhí)行,兩種方法:
l一種是是用exec命令來調(diào)用—用來測試存儲
exec過程名
l一種是用其他的程序(plsql和java)來調(diào)用
l?程序調(diào)用?
BEGIN
??sayhelloworld;
??sayhelloworld;
??sayhelloworld;
END;
帶書輸入?yún)?shù)IN
示例
查詢并打印某個員工(如7839號員工)的姓名和薪水--存儲過程:要求,調(diào)用的時候傳入員工編號,自動控制臺打印:
create or replace procedure p_queryempsal(i_empno IN emp.empno%TYPE)
IS
--聲明變量
v_ename emp.empname%TYPE;
v_sal emp.empsal%TYPE;
select empname,empsal into v_ename,v_sal from emp where empno=i_empno;
dbms_output.put_line('姓名:'||v_ename||',薪水:'||v_sal);
end?p_queryempsal;
--命令調(diào)用
exec?p_queryempsal(7878);
--程序調(diào)用
declare
i_empno emp.empno%TYPE:=8989;
BEGIN
p_queryempsal(i_empno?);
END;
?帶輸入?yún)?shù)IN和輸出結(jié)果OUT-----主要是其他程序調(diào)用
?示例:
----輸入員工號查詢某個員工(7839號(老大)員工)信息,要求,將薪水作為返回值輸出,給調(diào)用的程序使用。
CREATE?OR?REPLACE?PROCEDURE?p_queryempsal_out( i_empno IN?emp.empno%TYPE,o_sal OUT?emp.sal%TYPE)
AS
BEGIN
--賦值:將薪水的值賦給輸出的參數(shù)o_sal
??SELECT?sal INTO?o_sal FROM?emp WHERE?empno=i_empno; ?
END;
調(diào)用:
DECLARE
--輸入?yún)?shù)值
??v_empno emp.empno%TYPE:=7839;
--聲明一個變量來接收輸出參數(shù)
??v_sal?emp.sal%TYPE;
BEGIN
p_queryempsal_out(v_empno,v_sal);--第二個參數(shù)是輸出的參數(shù),必須有變量來接收??!
--當(dāng)上面的語句執(zhí)行之后,v_sal就有值了。
dbms_output.put_line('員工編號為:'||v_empno||'的薪資為:'||v_sal);
END;

java程序如何調(diào)用存儲過程:
//獲取連接
Connection conn = JDBCUtils.getConnection();
String sql="{call p_queryempsal_out(?,?)}";//轉(zhuǎn)義sql
CallableStatement call = conn.prepareCall(sql);
//1.輸入?yún)?shù)
call.setInt(1, 7839);//索引位置
call.registerOutParameter(2, OracleTypes.DOUBLE);//第一個參數(shù)是占位符,第二個參數(shù)數(shù)據(jù)類型
//執(zhí)行存儲
call.execute();//執(zhí)行的時候,會自動將參數(shù)傳入數(shù)據(jù)庫,將輸出參數(shù)返回的數(shù)據(jù),封裝會call對象中。
//獲取輸出參數(shù)的值
doublesal = call.getDouble(2);
System.out.println("薪資是:"+sal);
//釋放資源
JDBCUtils.release(conn, call,?null);
?結(jié)果如下:
