觸發(fā)器,概念一律不解釋!
CREATE
/*[DEFINER = { user | CURRENT_USER }]*/
TRIGGER `qqfs_db_gm`.`a` BEFORE/AFTER INSERT/UPDATE/DELETE
ON `qqfs_db_gm`.`<Table Name>`
FOR EACH ROW BEGIN
END
根據(jù)以上語(yǔ)法,做幾點(diǎn)解釋!
在解釋之前,闡述下我對(duì)觸發(fā)器的觀點(diǎn)!
由于我在游戲行業(yè),所面對(duì)的數(shù)據(jù),都是高并發(fā),讀寫(xiě)頻繁,但是數(shù)據(jù)并不一定海量!這個(gè)時(shí)候,我們對(duì)性能的要求非常高!觸發(fā)器,對(duì)性能影響過(guò)大!所以,在我們的幾個(gè)項(xiàng)目中,我從沒(méi)有引入觸發(fā)器!不過(guò)對(duì)于小數(shù)據(jù),或者是低并發(fā)、修改不頻繁的應(yīng)用,適當(dāng)?shù)囊胗|發(fā)器還是可以行的!
DEFINER:觸發(fā)器的創(chuàng)建者,可以手動(dòng)指定創(chuàng)建者,默認(rèn)為當(dāng)前用戶
BEFORE/AFTER:BEFORE,就是在觸發(fā)的動(dòng)作之前執(zhí)行你所想要執(zhí)行的語(yǔ)句(begin后面的sql語(yǔ)句);AFTER,在觸發(fā)動(dòng)作之后執(zhí)行你所想要的語(yǔ)句!
INSERT/UPDATE/DELETE:你所要觸發(fā)的條件。分別是insert、update、delete。這里不單單的針對(duì)這三個(gè)關(guān)鍵字,同樣的有同類效果的語(yǔ)句也會(huì)觸發(fā)!如LOAD DATA和REPLACE語(yǔ)句也會(huì)觸發(fā)insert
`qqfs_db_gm`.`<Table Name>`:觸發(fā)的對(duì)象都是表
語(yǔ)法解釋非常簡(jiǎn)單!需要注意以下幾點(diǎn):
1.觸發(fā)器里面不允許執(zhí)行動(dòng)態(tài)語(yǔ)句!或者是執(zhí)行帶動(dòng)態(tài)語(yǔ)句的存儲(chǔ)過(guò)程、存儲(chǔ)函數(shù)等!
2.對(duì)于具有相同觸發(fā)程序動(dòng)作時(shí)間和事件的給定表,不能有兩個(gè)觸發(fā)程序。例如,對(duì)于某一表,不能有兩個(gè)BEFORE UPDATE觸發(fā)程序。但可以有1個(gè)BEFORE UPDATE觸發(fā)程序和1個(gè)BEFORE INSERT觸發(fā)程序,或1個(gè)BEFORE UPDATE觸發(fā)程序和1個(gè)AFTER UPDATE觸發(fā)程序(官方說(shuō)明)
3.觸發(fā)的對(duì)象和觸發(fā)執(zhí)行的語(yǔ)句不能為同一個(gè)表!如:觸發(fā)器a觸發(fā)b表的insert操作,然后在b表執(zhí)行insert操作,會(huì)報(bào)錯(cuò)!這里應(yīng)該是觸發(fā)器的一種強(qiáng)制的鎖機(jī)制!所以就帶有很大的性能損耗!
4.不能讓兩個(gè)觸發(fā)器觸發(fā)兩個(gè)表,并使之循環(huán)!如:觸發(fā)器a觸發(fā)b表的insert操作,并往d表insert數(shù)據(jù);觸發(fā)器c觸發(fā)d表的insert操作,并往表b insert數(shù)據(jù);這樣是不行的!會(huì)報(bào)錯(cuò)如下:Can't update table 'test' in stored function/trigger because it is already used by statement which invoked this stored function/trigger.(第三點(diǎn)也會(huì)報(bào)這樣的錯(cuò)誤!)
5.觸發(fā)器中有new和old關(guān)鍵字。old是指老的數(shù)據(jù),很容易想到,會(huì)產(chǎn)生老數(shù)據(jù)的是update和delete操作,因?yàn)閕nsert之前沒(méi)有舊數(shù)據(jù)和該insert有直接關(guān)系!new關(guān)鍵字是指新數(shù)據(jù),同理可知道,delete操作是沒(méi)有新數(shù)據(jù)產(chǎn)生的,所有new關(guān)鍵字使用的觸發(fā)條件是insert和update!其實(shí)從這里可以看出,觸發(fā)器又保存了兩份數(shù)據(jù),結(jié)合上面的對(duì)表的觸發(fā)鎖定,觸發(fā)器的性能是不敢恭維的!
6.如果要在觸發(fā)update的同時(shí),修改該數(shù)據(jù)加1!用傳統(tǒng)的方法update table set id = old.id + 1;這樣肯定是不行的,違背了第三點(diǎn),會(huì)報(bào)錯(cuò):Can't update table 'test' in stored function/trigger because it is already used by statement which invoked this stored function/trigger.注意,這個(gè)錯(cuò)在觸發(fā)器編譯的時(shí)候,是能夠通過(guò)的,但是在更新的時(shí)候,數(shù)據(jù)庫(kù)會(huì)拋這個(gè)異常!
如果一定要這樣做,那該怎么辦呢?借助關(guān)鍵字new和old.
SET new.id = new.id + 1;
利用這個(gè)特性,可以實(shí)現(xiàn)很多功能!讀者可以自己發(fā)散,嘿嘿!
本文出自 “原下” 博客,請(qǐng)務(wù)必保留此出處http://qdjalone.blog.51cto.com/1222376/885501
聯(lián)系客服