--函数与存储过程的区别
/*
二者都是解决具体业务的问题
区别是:
1.在业务上:函数是具体功能的问题,而存储过程
还要解决系统接口的问题,垮软件和语言访问的
问题
2.在原理上,存储过程是预处理,预编译的。而函数
只是普通的语句 。预处理的结构他的整个IO读写
查询算法都需要存储到dbms,便于下次使用直接
获得结果,性能比函数快,但是这种预处理的结构
会占用更多的DBMS存储。
3.语法上,函数能解决的问题,存储过程都可以
4.在做具体项目的选材上,select结构一般都给函数
数据处理一般都给存储过程。
如果某一个业务结构要返回多个数据。需要采用
存储过程,因为函数只能返回单一的数据。
5.语法上。函数只能有一个返回,并通过returns定义
通过return返回。函数必须有一个返回
存储过程可以返回,也可以有多个返回。他的返回是
通过out定义的。存储过程不仅可以通过out返回。
还可以通过隐式返回。也就是说存储过程可以显示返回
也可以隐式返回。返回的方法多样。
函数只能select,存储过程,select,insert update delete
都可以。
*/
create table stu
(
sid int identity(1,1) primary key,
sname nvarchar(20)
)
insert into stu values('张三')
insert into stu values('李四')
insert into stu values('王五')
create table scos
(
ssid int identity(1,1) primary key,
sid int references stu(sid),
sco int,
km nvarchar(20)
)
insert into scos values (1,60,'c')
insert into scos values (2,90,'c++')
insert into scos values (2,70,'SQL server')
insert into scos values (3,60,'java')
select * from stu
select * from scos
--函数
--创建函数 findNameById 返回1行1列
create function findNameById
(
@sid int
)
returns nvarchar(20) --返回结果集 这种只能返回1行1列 ,有多行业只能得到最后一行的单元格
as
begin
declare @sname nvarchar(20)
select @sname=sname from stu where sid=@sid
return @sname
end
--删除函数
drop function findNameById
--执行函数
select dbo.findNameById(2) --必需加 dbo.
--这里使用函数,避免了笛卡尔积,提高了效率
select *,dbo.findNameById(sid) as 姓名 from scos
--创建函数 返回表格 为何return要放在上面 ????????
alter function getUsersScos
(
@sid int
)
returns table
as
return
select *,dbo.findNameById(sid) as 姓名 from scos
where sid=@sid
select * from dbo.getUsersScos(2)
--创建函数 返回表格
create function getUsersScos2
(
@sid int
)
returns @tmp table(ssid int,sid int,sco int,
km varchar(10),sname nvarchar(20))
as
begin
insert into @tmp
select *,dbo.findNameById(sid) as 姓名 from scos
where sid=@sid
return
end
select * from dbo.getUsersScos2(1)
--存储过程
/**
@desc:
@author:
@version:
*/
--隐式返回 sys_refcursor
create proc findById1
@id int
as
begin
select sname from stu where sid=@id
end
--显式返回
create proc findById2
@id int,
@name nvarchar(20) out
as
begin
select @name=sname from stu where sid=@id
end
--存储过程隐式返回的调用
--调用1
findById1 1
--调用2
exec findById1 1
execute findById1 1
--存储过程显式返回的调用
--调用2 --显示返回的调用
declare @tmp nvarchar(20)
begin
exec findById2 1,@tmp out
print @tmp
end
--游标
--指向当前行的指针,this
--场景:分析数据,抽奖,随机取样等
--常见问题:动静态游标的区别?
-- 游标都可以怎么移动?
-- 游标的语法是怎么样的?
--1.声明的for可以是任意sql
declare cur cursor for select sid,sname from stu
--2打开
open cur
--3.使用
--仅向前
fetch next from cur
--4.关闭
close cur
--5.释放
deallocate cur
--demo:将数据通过游标全部放入临时表
declare cur cursor for select sid,sname from stu
--2打开
open cur
--3.使用
--定义空的临时表
create table #tmp(sid int,sname nvarchar(20))
select * from #tmp
--仅向前
declare @id int
declare @name nvarchar(20)
fetch next from cur into @id,@name
while @@fetch_status=0 --游标状态 :当前有数据
begin
insert into #tmp values(@id,@name)
fetch next from cur into @id,@name--增量
end
--
--查看
select * from #tmp
--4.关闭
close cur
--5.释放
deallocate cur
--动态游标
declare cur scroll cursor for select * from scos
--打开
open cur
--使用
fetch first from cur --第一条
fetch prior from cur --前面一条
fetch next from cur --下一条
fetch last from cur --最后一条
fetch absolute 4 from cur --定位到第4条
fetch relative 2 from cur --定位到当前位置的下面第二条
close cur
deallocate cur
--触发器
--常用问题:
--1触发器的定义
--监控数据insert、update和delete的更改的行为
--PG可以通过建立日志和备份,防止用户错误的操作
--通过触发器还可以解决反范式用户对数据造成的不一致
--2.触发器监控的目标?、
--除了监控表,还能监控列?
--3.怎么通过触发器备份和建立日志呢?
--幻表,也叫虚表。其表结构是什么样的?
/*
-- inserted(:new) deleted(:old)
select N N
insert Y N
delete N Y
update Y Y
*/
--4.触发器在何时监控?
--创建触发器 给表
create trigger tri1
on stu
after insert,delete,update
as
begin
select '新'
select * from inserted --新的幻表(这样好理解些)
select '老'
select * from deleted --旧的幻表
end
insert into stu values('张佳')
select * from stu
--修改触发器 给表的某列加触发器(下面的例子新增也会触发,)
alter trigger tri1
on stu
after insert,delete,update
as
begin
if update(sname)
begin
select '您修改的此列,此列不允许修改'
rollback tran
end
end
drop trigger tri1
update stu set sname='张三1' where sid=1
insert into stu values('伍佰')
--监控用户表的所有行为,把用户对数据的更改(触发器的详细例子)
--自动备份到日志表
select * from stu
create table stulog(
sid int,
sname nvarchar(20),
type varchar(50),
updatetime datetime
)
alter trigger tri2
on stu
after insert,delete,update
as
begin
declare @id int
declare @name varchar(20)
IF EXISTS(SELECT 1 FROM inserted) AND NOT EXISTS(SELECT 1 FROM deleted)
begin
--新增触发
select @id=sid,@name=sname from inserted
insert into stulog values(@id,@name,'insert',getdate())
end
else IF EXISTS(SELECT 1 FROM inserted) AND EXISTS(SELECT 1 FROM deleted)
begin
--修改触发
select @id=sid,@name=sname from deleted
insert into stulog values(@id,@name,'updateBefore',getdate()) --修改之前的数据
select @id=sid,@name=sname from inserted
insert into stulog values(@id,@name,'updateAfer',getdate()) --修改之后的数据
end
else
begin
--删除触发
select @id=sid,@name=sname from deleted
insert into stulog values(@id,@name,'delete',getdate())
end
end
insert into stu values('黎明')
--创建视图
create view V_STUSCO
as
select a.sid,sname,b.km,b.sco from stu a
inner hash join scos b on a.sid=b.sid
select * from V_STUSCO
select * from stu
select * from scos
insert into V_STUSCO values(3,'e','yoga',80)
--我们不能给这个视图插入数据 因为该视图有多个基表 需要通过 instead of 触发器来完成
create trigger ttri
on V_STUSCO
instead of insert
as
begin
declare @id int
declare @newId int
declare @name nvarchar(20)
declare @km nvarchar(20)
declare @sco int
--取得幻表数据
select @id=sid,@name=sname,@km=km,@sco=sco from inserted
--数据转储到基表
insert into stu values(@name) --新增学生信息
--由于id是自动获取。所以我们要查处id
select @newid=sid from stu where sname=@name --获得新增学生的id,scos需要用到
insert into scos values(@newid,@sco,@km)
end
select * from V_STUSCO
--通过视图插入
insert into V_STUSCO values(5,'王佩','yoga',90) --这里的5没有用,只是为了列的一一对应,少写列名
select * from stu
select * from scos
分享到:
相关推荐
这份"oracle笔记(存储过程函数触发器游标流程控制等)"涵盖了Oracle数据库管理中的关键知识点,包括但不限于以下几个方面: 1. **存储过程与函数**:存储过程是预编译的SQL语句集合,用于执行特定任务。它们可以提高...
Oracle数据库是世界上最流行的数据库管理系统之一,它提供了丰富的功能来处理数据,包括函数、游标和触发器。在本文中,我们将深入探讨这些概念,并通过一些实际的例子来理解它们的用法。 1. **Oracle函数**:函数...
总的来说,掌握SQL的高级应用,尤其是存储过程、触发器和游标,能够使开发者更好地实现数据库的复杂逻辑和业务需求,提高数据库系统的整体效能。在学习过程中,可以结合实际项目,通过实践来加深理解和运用这些技术...
6. 存储过程修改与变更:在对SQLServer存储过程进行修改和变更时,可能会遇到与现有数据库函数冲突的问题,需要掌握正确的方法来进行升级和批量修改,避免造成错误。 7. 异常处理的详细机制:在TRY块中包含潜在失败...
执行存储过程时,可以使用EXEC或者sp_executesql函数。 在实际应用中,存储过程和触发器经常协同工作。例如,一个存储过程可能被触发器调用,以便在数据更改后执行附加的业务逻辑。同时,存储过程也可以在业务层...
本主题将深入探讨Oracle中的几个核心概念:函数、存储过程、游标以及简单的实例,这些都是数据库管理员和开发人员日常工作中不可或缺的部分。 首先,我们来了解**Oracle函数**。函数是预定义的代码块,接受零个或多...
### SQL Server 存储过程与触发器详解 #### 一、存储过程概述 **存储过程**是在数据库中预编译并存储的一组SQL语句,它可以在SQL Server中执行复杂的数据处理逻辑。存储过程不仅可以提高应用程序的性能,还能增强...
MySQL是世界上最流行的开源关系型数据库管理系统之一,它包含多种功能,如函数、存储过程、触发器和游标,这些功能极大地增强了数据库管理的灵活性和效率。以下是对这些概念的详细解释: 1. **MySQL函数**:MySQL...
存储过程、函数和触发器是PL/SQL中的核心概念,它们在数据库管理中扮演着至关重要的角色。 一、存储过程 存储过程是一组预编译的SQL语句和PL/SQL代码,可以视为数据库中的可执行对象。它们允许开发者封装一系列的...
存储过程是数据库中一组预编译的SQL语句,它可以接收参数,执行特定任务,并返回结果。其优点包括: 1. 提高性能:存储过程在首次编译后,会缓存执行计划,多次调用时无需再次解析,从而提高执行速度。 2. 减少网络...
PL/SQL函数和过程可以使用Oracle的函数和过程语法来编写,而Transact-SQL函数和过程则需要使用SqlServer的函数和过程语法。 例如,Oracle的PL/SQL函数可以这样编写: ```plsql CREATE OR REPLACE FUNCTION get_...
视图、存储过程、函数、游标与触发器ppt资源,详细讲解,分享给有需要朋友。
2. **包**:包是PL/SQL的一个高级特性,它可以封装一组相关的常量、变量、过程和函数。包由两部分组成:包规范(声明部分)和包主体(实现部分)。包规范定义了包的公共接口,而包主体包含了具体的实现代码。包的...
这个压缩包“PLSQL操作存储过程、函数、游标、触发器、定时任务等实例SQL脚本.zip”包含了关于如何使用PL/SQL来处理数据库的各种关键概念的实例脚本。下面,我们将详细探讨这些知识点。 1. **存储过程**:存储过程...
### 自定义函数、存储过程和触发器 #### 9.1 自定义函数 ...通过学习自定义函数、存储过程和触发器的概念、用途及创建方法,可以更好地利用SQL Server的强大功能,提高数据库应用程序的性能和可靠性。
综上所述,MySQL中的索引、视图、触发器、游标、事务和存储过程都是高级特性,这些工具可以帮助开发人员更好地管理和操作数据库。通过对这些概念的理解和实践,可以大幅提升数据库应用的性能和可靠性。
在数据库系统中,游标、存储过程和触发器是三个高级技术,它们在复杂逻辑处理和数据管理方面扮演着核心角色。本文将详细解析实验六中这些概念的实现方式,包括具体的示例和操作步骤,以期帮助数据库管理员和开发人员...
本套教程全面覆盖了Oracle数据库的核心编程元素,包括存储过程、函数、触发器、异常处理、游标和存储包,这些都是数据库开发和管理中的关键概念。 首先,我们来详细了解存储过程。存储过程是一组预编译的SQL语句,...
这在创建存储过程、触发器等数据库对象时尤其重要,因为非确定性函数可能无法在某些对象中使用。 理解SQL Server的函数大全对于有效的数据库管理和查询优化至关重要,它们提供了一种灵活、强大的方式来处理和分析...