首頁  >  文章  >  資料庫  >  mysql預存程序和觸發器的區別

mysql預存程序和觸發器的區別

(*-*)浩
(*-*)浩原創
2019-05-09 16:00:064407瀏覽

mysql預存程序是在大型資料庫系統中, 一組為了完成特定功能的SQL語句集;而觸發器是一種特殊類型的預存程序;觸發器不同於預存程序,觸發器主要是透過事件進行觸發而被執行的,而預存程序可以透過預存程序名字而直接呼叫。

mysql預存程序和觸發器的區別

預存程序: 是在大型資料庫系統中, 一組為了完成特定功能的SQL 語句集。觸發器:觸發器是一種特殊類型的預存過程,它又不同於預存程序,觸發器主要是透過事件進行觸發而被執行的,而預存程序可以透過預存程序名字而直接呼叫。

預存程序:
是在大型資料庫系統中,
一組為了完成特定功能的SQL 語句集,
儲存在資料庫中,經過第一次編譯後再次呼叫不需要再次編譯,
使用者透過指定預存程序的名字並給出參數(如果該預存程序帶有參數)來執行它。
預存程序是資料庫中一個重要的物件

優點:
1允許模組化程式設計(創建一次多次使用)
2允許更快執行
3減少網絡流量
4更好的安全機制

格式:

DELIMITER // 
CREATE PROCEDURE 储存名([ IN ,OUT ,INOUT ]?参数名?数据类形...) 
BEGIN 
SQL语句 
END // 
DELIMITER ;

呼叫過程:

用call 過程名稱( )

查看所有的存儲過程show procedure status; 
查看已建立的預存程序show create procedure 過程名稱; 
刪除過程drop procedure 過程名稱

In 表示參數從外部傳入到裡面使用(過程內部使用)
Out 表示參數從過程裡邊把資料保存到變數中,交給外部使用,所有傳入的必須是變數如果說傳入的out變數本身在外部有數據,那麼在進入過程之後,第一件事就是被清空,設為null
Inout 資料可以從外部傳入到過程內部使用,同時內部操作之後,又會將資料回傳給外部

 

觸發器:

觸發器是一種特殊類型的預存過程,它又不同於預存程序,
觸發器主要是透過事件進行觸發而被執行的,而預存程序可以透過儲存過程名字而直接呼叫。

作用:
1.可在寫入資料表前,強制檢驗或轉換資料 
2.觸發器發生錯誤時,異動的結果會被撤銷

格式

DELIMITER //
Create trigger --触发器名字 触发时机 触发事件 on 表 for each 
row 
Begin 
--操作的内容 
End // 
DELIMITER ;

觸發物件:on 表for each row 觸發器綁定實質是表中的所有行,因此當每一行發生改變的時候,就會觸發觸發器 
觸發時機:每張表中對應的行都會有不同的狀態,當SQL 指令發生的時候,
都會令行中的資料改變,每一行總會有兩個狀態。操作資料之前(before),操作資料(after)之後
觸發事件:
Mysql中觸發器針對的目標是資料改變,對應的操作只有(增,刪,改)查詢不發生資料的改變,
所以查詢沒有觸發事件
注意事項:
一張表中,每一個觸發器時機綁定的觸發事件對應的觸發器類型只能有一個;
一張表中只能有一個after insert 觸發器因此,一張表中最多的觸發器只能有六個

建立預存程序

DELIMITER //
CREATE PROCEDURE addUser
(IN uCode VARCHAR(50),IN uName VARCHAR(20),IN uRole INT,IN sex INT,IN tel VARCHAR(30))
BEGIN
INSERT INTO smbms_user (userCode,userName,userRole,gender,phone)
VALUES(uCode,uName,uRole,sex,tel);
END//
DELIMITER //
查看存储过程 show procedure status;
<insert id="saveUser">
CALL addUser(#{userCode},#{userName},#{userRole},#{gender},#{phone})
</insert>
public int saveUser(
@Param("userCode") String userCode,
@Param("userName") String userName,
@Param("userRole") Integer userRole,
@Param("gender") Integer gender,
@Param("phone") String phone);
public List<User> findUserListPage(String queryUserName, 
Integer queryUserRole, 
Integer currentPageNo, Integer pageSzie);

public boolean saveUser(String userCode, String userName, Integer userRole,
Integer gender, String phone) {
SqlSession sqlSession = null;
int row = 0; // 受影响的行数
try {
sqlSession = MyBatisUtil.createSqlSession();
row = sqlSession.getMapper(UserMapper.class).saveUser(userCode, userName, userRole, gender, phone);
// 提交事务
sqlSession.commit();
} catch (Exception e) {
if (sqlSession != null) {
sqlSession.rollback();
}
row = 0;
e.printStackTrace();
} finally {
MyBatisUtil.closeSqlSession(sqlSession);
}
if (row > 0) {
return true;
}
return false;
}

userService.saveUser("zhangcuishan", "亚索", 1, 2, "15645678941");

建立觸發器

创建两张表
create table my_goods(
id int primary key auto_increment,
name varchar(20) not null,
inv int
)
create table my_orders(
id int primary key auto_increment,
goods_id int not null,
goods_num int not null)

insert into my_goods values(null,'手机',1000),(null,'电脑',500),(null,'游戏机',100);

DELIMITER //
CREATE TRIGGER a_i_o_t AFTER INSERT ON my_orders FOR EACH ROW
BEGIN
UPDATE my_goods SET inv =inv -new.goods_num WHERE id=new.goods_id;
END
//
DELIMITER ;

DELIMITER //
CREATE TRIGGER b_i_o_t BEFORE INSERT ON my_orders FOR EACH ROW 
BEGIN 
SELECT inv FROM my_goods WHERE id=new.goods_id INTO @inv;
IF @inv <new.goods_num THEN 
INSERT INTO xxx VALUES('xx');
END IF;
END 
//
DELIMITER //
 

测试 insert into my_orders values(null,3,5);

以上是mysql預存程序和觸發器的區別的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn