对数据库触发器new和old的理解
在数据库的触发器中经常会用到更新前的值和更新后的值,所有要理解new和old的作用很重要。当时我有个情况是这样的:我要插入一行数据,在行要去其他表中获得一个单价,然后和这行的数据进行相乘的到总金额,将该行的金额替换成相乘的结果。
一开始我使用的after,然后对自身的值进行更改。
| insert | update | delete | |
|---|---|---|---|
| old | null | 实际值 | 实际值 |
| new | 实际值 | 实际值 | null |
在Oracle中用:old和:new表示执行前的行,和执行后的行。在MySQL中用old和new表示执行前和执行后的数据。
问题的起源
之前对数据库的触发器是这样写的,
CREATE TRIGGER triggerName after insert ON consumeinfo
FOR EACH ROW
BEGIN
UPDATE consumeinfo SET new.金额=0;
END;
触发器创建没问题,但是插入数据出现以下错误。
[Err] 1442 - Can't update table 'consumeinfo' in stored function/trigger because it is already used by statement which invoked this stored function/trigger.
但是通过上网搜索的结果说对本表进行修改不用使用update consumeinfo,直接使用SET new.金额=0。这个做法对的,因为这样使用new先对当前的金额改变了,然后存到数据库中的,不用使用update consumeinfo。
经过一番努力,以下是成功后的代码,贴出来看看
CREATE TRIGGER addnewReco BEFORE INSERT ON consumeinfo FOR EACH ROW
BEGIN
SET new.金额 = (
SELECT `单价`
FROM pricenow
WHERE `类型` = new.类型
) * new.数量;
END;
后来在吃饭打汤喝的时候突然想到new和old在after和before上使用情况不同。其实还是因为new不能在after进行赋值,只能进行读取,复制要在before时赋值。
new和old的使用情况
下面具体说说old和new的使用情况。在对new赋值的时候只能在触发器before中只用,在after中是不能使用的,比如(以下是正确的)。
CREATE TRIGGER updateprice
BEFORE insert
ON consumeinfo
FOR EACH ROW
BEGIN
set new.金额=0;
END;
这个说明对当前插入数据进行更新的时候使用before先更新完,然后才插入到数据库中的,在after的触发器中,new的赋值已经结束了,只能读取内容。 如果使用after不能使用new赋值,只能取值,否则会出错误,比如
CREATE TRIGGER updateprice
AFTER insert
ON consumeinfo
FOR EACH ROW
BEGIN
set new.金额=0;
END;
出现这样的错误:
[Err] 1362 - Updating of NEW row is not allowed in after trigger
|
|
|
总结:new在before触发器中赋值,取值;在after触发器中取值。old在用于取值?因为赋值没意义?
对数据库触发器new和old的理解的更多相关文章
- Mysql数据库触发器调用脚本
一.数据库触发器 mysql触发器trigger 实例详解 对数据库触发器new和old的理解 示例 二.UDF mySql的UDF是什么 三.安装执行命令UDF mysql触发器调用外部脚本(安装) ...
- 数据库触发器new old
数据库触发器new old: "NEW . column_name"或者"OLD . column_name".这样在技术上处理(NEW | OLD . col ...
- sqlserver数据库触发器调用外部exe
sqlserver数据库触发器调用外部exe,同事可以选择参入参数! sqlserver使用 master..xp_cmdshell 进行外部exe的执行. 使用master..xp_cmdshell ...
- 数据库级别DDL操作监控审计、数据库触发器/服务器触发器
关键词:数据库触发器/服务器触发器 ,数据库级别DDL操作监控审计,禁止修改登录名密码 [1]数据库级别DDL操作监控审计 转自2012示例库,只能数据库级别,不能实例级别 use database ...
- Oracle12c中多宿主环境(CDB&PDB)的数据库触发器(Database Trigger)
Oracle12c中可插拔数据库(PDBs)上的多宿主数据库触发器 随着多宿主选项的引入,数据库事件触发器可以在CDB和PDB范围内创建. 1. 触发器范围 为了在CDB中创建数据库事件触发器,需 ...
- SQL 数据库 触发器 、事务
触发器类型有两种: 1.AFTER(FOR)触发器 在动作执行之后触发(增删改执行完成后,触发器中的代码再执行),不能为视图指定for触发器,只能为表指定该触发器. 2.instead of触发器 可 ...
- Oracle数据库——触发器的创建与应用
一.涉及内容 1.理解触发器的概念.作用和类型. 2.练习触发器的创建和使用. 二.具体操作 (实验) 1.利用触发器对在scott.emp表上执行的DML操作进行安全性检查,只有scott用户登录数 ...
- mysql数据库 触发器简单实例
触发器(trigger):监视某种情况,并触发某种操作. 触发器创建语法四要素:1.监视地点(table) 2.监视事件(insert/update/delete) 3.触发时间(after/befo ...
- oracle 添加登陆数据库触发器--记录IP 地址
----触发器--- ---创建中间插入的表 create table session_history tablespace bap_data as (select sid,username,prog ...
随机推荐
- jQuery常用API
jQuery API查询网址 http://jquery.cuishifeng.cn/ Dom和jquery相互装换 jquery对象[0] => Dom对象 Dom对象 => $(Dom ...
- Java abstract
abstract修饰符可以修饰类和方法. (1)abstract修饰类,会使这个类成为一个抽象类,这个类将不能生成对象实例,但可以做为对象变量声明的类型,也就是编译时类型.抽象类就相当于一类的半成品, ...
- devstack meaning of: n-cond, n-novnc and n-xvnc
devstack has shortened names for a number of services, e.g. g-api = glance api g-reg = glance regist ...
- Git引用
原文: http://gitbook.liuhui998.com/7_3.html git中,分支(branch), 远程跟踪分支(remote-tracking branch)以及标签(tag)都是 ...
- iOS coredata 数据库升级 时报Can't find model for source store
在coredata 数据库结构被更改后,没根据要求立即建立新version,而是在原version上进行了小修改,之后才想起来建立新版本.并通过以下代码合并数据库, NSError *error = ...
- 安装CentOS 7时出现No Caching mode page found问题的解决
将CentOS 7镜像刻到U盘之后,向服务器安装时,使用U盘启动会出现两种启动选项,一种是UEFI启动选项,一种是默认的启动选项,如果不使用UEFI方式安装,那么一般是没有问题的,如果选择UEFI方式 ...
- 一名Delphi程序员的开发习惯
一名Delphi程序员的开发习惯 有关开发习惯的一些想法,如鲠在喉,不吐不快.究其发贴动机,当然不排除有骗取参与分的可能,但另一方面,也希望能给同行(念Xing)者提供一些 建议,或者参考(希望不是误 ...
- ACM/ICPC 之 判别MST唯一性-Kruskal解法(POJ1679)
判别MST是否唯一的例题. POJ1679-The Unique MST 题意:给定图,求MST(最小生成树)是否唯一,唯一输出路径长,否则输出Not Unique! 题解:MST是否唯一取决于是否有 ...
- 10. javacript高级程序设计-DOM
1. DOM DOM(文档对象模型)是针对HTML和XML文档的一个API(应用程序接口) 1.1 节点层次 DOM可以将任何HTML和XML文档描绘成一个由多层节点构成的结构.节点分为几种不同的类型 ...
- ajax与后台交互传输数据的工具类
public class Result<T> implements Serializable { private static final long serialVersionUID = ...