❶ 存储过程的触发器
触发器是一种特殊类型的存储过程,它不同于我们前面介绍过的存储过程。触发器主要是通过事件进行触发而被执行的,而存储过程可以通过存储过程名字而被直接调用。当对某一表进行诸如Update、 Insert、 Delete 这些操作时,sql Server 就会自动执行触发器所定义的SQL 语句,从而确保对数据的处理必须符合由这些SQL 语句所定义的规则。
触发器的主要作用就是其能够实现由主键和外键所不能保证的复杂的参照完整性和数据的一致性。除此之外,触发器还有其它许多不同的功能:
(1) 强化约束(Enforce restriction)
触发器能够实现比CHECK 语句更为复杂的约束。
(2) 跟踪变化Auditing changes
触发器可以侦测数据库内的操作,从而不允许数据库中未经许可的指定更新和变化。
(3) 级联运行(Cascaded operation)。
触发器可以侦测数据库内的操作,并自动地级联影响整个数据库的各项内容。例如,某个表上的触发器中包含有对另外一个表的数据操作(如删除,更新,插入)而该操作又导致该表上触发器被触发。
(4) 存储过程的调用(Stored procere invocation)。
为了响应数据库更新,触发器可以调用一个或多个存储过程,甚至可以通过外部过程的调用而在DBMS(数据库管理系统)本身之外进行操作。
由此可见,触发器可以解决高级形式的业务规则或复杂行为限制以及实现定制记录等一些方面的问题。例如,触发器能够找出某一表在数据修改前后状态发生的差异,并根据这种差异执行一定的处理。此外一个表的同一类型(Insert、 Update、 Delete)的多个触发器能够对同一种数据操作采取多种不同的处理。
总体而言,触发器性能通常比较低。当运行触发器时,系统处理的大部分时间花费在参照其它表的这一处理上,因为这些表既不在内存中也不在数据库设备上,而删除表和插入表总是位于内存中。可见触发器所参照的其它表的位置决定了操作要花费的时间长短。 SQL Server 2000 支持两种类型的触发器:AFTER 触发器和INSTEAD OF 触发器。其中AFTER触发器即为SQL Server 2000 版本以前所介绍的触发器。该类型触发器要求只有执行某一操作(Insert Update Delete) 之后,触发器才被触发,且只能在表上定义。可以为针对表的同一操作定义多个触发器。对于AFTER触发器,可以定义哪一个触发器被最先触发,哪一个被最后触发,通常使用系统过程sp_settriggerorder 来完成此任务。
INSTEAD OF触发器表示并不执行其所定义的操作(Insert、 Update、 Delete),而仅是执行触发器本身。既可在表上定义INSTEAD OF触发器,也可以在视图上定义INSTEAD OF 触发器,但对同一操作只能定义一个INSTEAD OF 触发器。 Create procere procere_name
[@parameter data_type][output]
[with]{recompile|encryption}
as
sql_statement
解释:
output:表示此参数是可传回的
with {recompile|encryption}
recompile:表示每次执行此存储过程时都重新编译一次
encryption:所创建的存储过程的内容会被加密
如:
表book的内容如下
编号 书名 价格
001 C语言入门 $30
002 PowerBuilder报表开发 $52
实例1:查询表Book的内容的存储过程
create proc query_book
as
select * from book
go
exec query_book
实例2:
加入一笔记录到表book,并查询此表中所有书籍的总金额 Createprocinsert_book@param1char(10),@param2varchar(20),@param3money,@---------加密asinsertintobook(编号,书名,价格)Values(@param1,@param2,@param3)select@param4=sum(价格)frombookgo执行例子:declare@total_pricemoneyexecinsert_book顛','Delphi控件开发指南',$100,@total_priceoutputprint'总金额为'+convert(varchar,@total_price)go存储过程的3种传回值:
1)、以Return传回整数
2)、以output格式传回参数
3)、Recordset
传回值的区别:
output和return都可在批次程式中用变量接收,而recordset则传回到执行批次的客户端中。
实例3:
设有两个表为Proct,Order_,其表内容如下:
Proct
产品编号 产品名称 客户订数
001 钢笔 30
002 毛笔 50
003 铅笔 100
Order_
产品编号 客户名 客户订金
001 南山区 $30
002 罗湖区 $50
003 宝安区 $4
请实现按编号为连接条件,将两个表连接成一个临时表,该表只含编号.产品名.客户名.订金.总金额,
总金额=订金*订数,临时表放在存储过程中
代码如下:
Create proc temp_sale
as
select a.产品编号,a.产品名称,b.客户名,b.客户订金,a.客户订数* b.客户订金 as总金额
into #temptable from Proct a inner join Order_ b on a.产品编号=b.产品编号-----此处要用别名
if @@error=0
print 'Good'
else
print 'Fail'
go
❷ 存储过程的调用与触发器的调用有何区别
存储过程在你需要使用的时候自行调用,触发器在发生某件事情的时候自动调用。如Insert触发器,当表Insert数据的时候自动就执行了触发器里面的代码
❸ oracle触发器怎么调用存储过程,不用传参数和传参数都行
直接调用就可以了,但是存储过程中不能有显示的事务控制,例如commit;rollback;ddl。如果必须的,需要使用自治事务。使用自治事务时尽量避免对触发器的宿主表进行操作,容易造成死锁
❹ mysql!触发器里如何调用存储过程。
call showChildLst(new.pn,new.pa)
❺ 触发器调存储过程问题。求解。
我感觉可能跟系统的锁机制有关,触发器中插入数据,此时一般是需要锁表的,如果默认是表级锁,那么在过程里面select也是不行的。你可以修改一下过程,暂时不从"表a" select数据,换一个表,如果可以,那应该就是这个原因。如果select from其它表也不行,就是别的原因了。
❻ 如何用触发器调用存储过程!!
create trigger [owner.]trigger_name
on[owner.]table_name
{for insert}
as
sql_statement
顺便问下:你的rollback怎么写在begin里了
❼ 您说:触发器可以调用存储过程. 触发器中调用存储过程会提高系统效率
我不知道你是在哪里看到的这个逻辑,虽然存储过程是经过预先编译并存储在数据库中的,但一般来说,触发器是种特殊的存储过程,所以本质上并无谁快谁慢的问题,正如你说疑惑的,本身就属于简单业务逻辑的SQL是否还有必要通过触发器再去调用一次存储过程,带来复杂开销。
触发器本身是在每一笔记录产生变化的时候发生的,一般用于数据完整性的一些检查,不建议写太复杂的逻辑,或者是程序更新之前一种临时性的解决方案,业务逻辑,还是建议以程序+存储过程,当然这是站在系统建设的规划、长期维护基础上。
所以,如果仅仅是当时不方便更新程序,然后用触发器来调用现有的逻辑,这个倒是一个不错的临时解决方案,毕竟系统的业务顺畅第一位。
❽ 如何在触发器中调用存储过程
在触发器中调用存储过程:
CREATEtriggermalice
onBBSUser
forupdate
as
ifupdate(receive)--当receive字段发生update事件时触发
begin
updatebbsuser
setreceive_temp=bu.receive_temp+(i.receive-d.receive)
frombbsuserbu,deletedd,insertedi
wherebu.userid=i.userid
declare@tempfloat,@scopefloat
set@temp=(selectbb.receive_tempfrombbsuserbb,deleteddwherebb.userid=d.userid)
set@scope=(selectbb.receive_scopefromBBSUserbb,deleteddwherebb.userid=d.userid)
if@temp<=@scope
updateuserinfo
setstandnumber=bu.standnumber+(i.receive-d.receive)
fromuserinfobu,deletedd,insertedi
wherebu.userid=d.userid
declare@userint,@comfloat
select@user=d.userid,@com=us.standnumber
fromUserInfous,Deletedd,Insertedi
whereus.userid=d.userid
exectimely@user,@com
if@temp>@scope
begin
updateuserinfo
setstandnumber=bu.standnumber+(@scope-d.receive)
fromuserinfobu,deletedd,insertedi
wherebu.userid=d.userid
updatebbsuser
setreceive_temp=@scope
frombbsuserbu,deletedd
wherebu.userid=d.userid
select@user=d.userid,@com=us.standnumber
fromUserInfous,Deletedd,Insertedi
whereus.userid=d.userid
exectimely@user,@com
end
end
❾ Oracle 触发器调用存储过程
通过配置本地数据库的tns配置文件实现:
去oracle安装目录下oracle\proct\10.2.0\db_2\NETWORK\ADMIN\ 找到tnsnames.ora,用记事本打开,里边有远程数据库的tns连接配置串如下
ORCL23 =
(DESCRIPTION =
(ADDRESS_LIST =
(ADDRESS = (PROTOCOL = TCP)(HOST = 192.168.3.23)(PORT = 1521))
)
(CONNECT_DATA =
(SID = ORCL)
)
)
添加好ip、端口和目标数据库的实例名(SID),然后确保tns名称(ORCL23)在整个文档中唯一,保存后打开数据库连接工具,输入远程数据库上的用户名密码,选择数据库对象为你配置的连接名就可以了
❿ sql中的触发器与存储过程有什么相同点和不同点希望能专业点,谢谢
一、功能不同:
1、存储过程的功能:
(1) 变量说明
(2) ANSI(美国国家标准化组织)兼容的SQL命令(如Select,Update….)
(3) 一般流程控制命令(if…else…、while….)
2、触发器的功能:
(1)强化约束(Enforce
restriction)
(2)跟踪变化Auditing
changes
(3)级联运行(Cascaded
operation)
二、指代不同
存储过程:在大型数据库系统中,一组为了完成特定功能的SQL语句集。
触发器:SQL server 提供给程序员和数据分析员来保证数据完整性的一种方法。
三、作用不同:
1、存储过程:局时存储过程,以两个井字号(##)号开始,则该存储过程将成为一个存储在tempdb数据库中的全局临时存储过程,全局临时存储过程一旦创建,以后连接到服务器的任意用户都可以执行它,而且不需要特定的权限。
2、触发器:可用于强制引用完整性,以便在多个表中添加、更新或删除行时,保留在这些表之间所定义的关系。然而,强制引用完整性的最好方法是在相关表中定义主键和外键约束。
四、相同点:
触发器是自动的:它们在对表的数据作了任何修改(比如手工输入或者应用程序采取的操作)之后立即被激活。
触发器可以通过数据库中的相关表进行层叠更改。例如,可以在 titles 表的 title_id 列上写入一个删除触发器,以使其它表中的各匹配行采取删除操作。该触发器用 title_id 列作为唯一键,在 titleauthor、sales 及 roysched 表中对各匹配行进行定位。
触发器可以强制限制,这些限制比用 CHECK 约束所定义的更复杂。与 CHECK 约束不同的是,触发器可以引用其它表中的列。
(10)用触发器调用存储过程扩展阅读:
触发器可通过数据库中的相关表实现级联更改;通过级联引用完整性约束可以更有效地执行这些更改。触发器可以强制用比 CHECK 约束定义的约束更为复杂的约束。与CHECK约束不同,触发器可以引用其它表中的列。例如,触发器可以使用另一个表中的 SELECT 比较插入或更新的数据,以及执行其它操作,如修改数据或显示用户定义错误信息。
触发器也可以评估数据修改前后的表状态,并根据其差异采取对策。