Oracle動態sql,觸發器,函式,exists
阿新 • • 發佈:2018-12-15
1.動態SQL
後期聯編(late binding),即SQL語句只有在執行階段才能建立,例如當查詢條件為使用者輸入時,那麼Oracle的SQL引擎就無法在編譯期對該程式語句進行確定,只能在使用者輸入一定的查詢條件後才能提交給SQL引擎進行處理。
語法:
Excute immediate 動態SQL語句 into 輸出引數列表 using 繫結引數列表 ;
create or replace procedure proc(e_id emp.eid%type)
as
e_name emp.ename%type;
begin
execute immediate 'select ename from emp where eid=:1' into e_name using e_id;
dbms_output.put_line('名字為:' ||e_name);
end;
2.觸發器
觸發器的定義就是說某個條件成立的時候,觸發器裡面所定義的語句就會被自動的執行。 因此觸發器不需要人為的去呼叫,也不能呼叫。 然後,觸發器的觸發條件其實在你定義的時候就已經設定好了。
語句級觸發器:某條語句執行前或後出發 行級觸發器:表中的行資料改變時就會觸發一次 語法結構: create [or replace] trigger triggername (觸發時間)[before/after] 觸發事件 on 表名 [for each row]--對錶的每一行觸發器執行一次。如果沒有這一選項,則只對整個表執行一次 begin pl/sql語句 end CREATE [OR REPLACE] TRIGGER trigger_name {BEFORE | AFTER } {INSERT | DELETE | UPDATE [OF column [, column …]]} [OR {INSERT | DELETE | UPDATE [OF column [, column …]]}...] ON [schema.]table_name | [schema.]view_name [REFERENCING {OLD [AS] old | NEW [AS] new| PARENT as parent}] [FOR EACH ROW ] [WHEN condition] PL/SQL_BLOCK | CALL procedure_name;
create or replace trigger mytrigger
before insert or update or delete
on emp
begin
if(to_char(sysdate,'DY')='星期四') then
raise_application_error(-20001,'b不能再星期四修改emp表資料');
end if;
end;
error_number是範圍在-20000到-20999之間的負整數, error_message是最大長度為2048位元組的字串, keep_errors是一個可選的布林值,True表示新的錯誤將被新增到已經丟擲的錯誤列表中,False表示新的錯誤將替換當前的錯誤列表,預設為False。
3.函式
create or replace function get_salsum(dept_id number,total_count out number)
return number
as
v_sumsal number(10) := 0;
//定義遊標,進行迴圈疊加
cursor salary_cursor is select salary from employees where department_id = dept_id;
begin
total_count := 0;
for c in salary_cursor loop
v_sumsal := v_sumsal +c.salary;
total_count := total_count + 1;
end loop;
return v_sumsal;
end;
呼叫:
dbms_output.put_line(get_salsum(80,v_num));
dbms_output.put_line(v_num);
4.sql優化問題–exists
exists 存在,返回值是true not exists 不存在,返回值是false
select sysdate from dual where (select count(*) from emp where eid='1001')=1;
select sysdate from dual where not exists(select * from emp where eid='1005');
1. in()適合B表比A表資料小的情況
2. exists()適合B表比A表資料大的情況
3.當A表資料與B表資料一樣大時,in與exists效率差不多,可任選一個使用.
select * from A
where id in(select id from B)
select a.* from A a
where exists(select 1 from B b where a.id=b.id)
minus 取得差集 intersect 取得交集 union 取得並集 union all 不過濾重複的部分