数据库 基础学习7— 数据库编程

一、变量的定义与赋值

 

declare @变量名 类型

set @变量名=值

eg、

--查汽车表中名称含有宝马两个字的
declare @name varchar(20)
set @name='宝马'
select * from car where Name like '%'+@name+'%'

-- 查汽车表中所有汽车的平均值并输出
declare @price decimal(10,4)
select @price = AVG(Price) from Car
print '所有汽车的平均价格为:'+cast(@price as varchar(20))

 

二、语句

1、输出语句  print '字符串'

2、分支语句

a、if else 

1 if 判断条件
2 begin 
3   要执行的语句
4 end
5 else
6 begin
7   要执行的语句
8 end

 

b、case  语句(相当于C#的swtich case)(两种用法)

1.简单Case函数

CASE sex

         WHEN '1' THEN ''

         WHEN '2' THEN ''

ELSE

  '其他'

END

 

2.Case搜索函数

CASE

   WHEN sex = '1' THEN ''

     WHEN sex = '2' THEN ''

ELSE

  '其他'

END

 

eg1、

1 declare @ccname varchar(20)
2 set @ccname = '宝马'
3 select * from Car where Name like 
4 case
5   when @ccname='宝马' then '%宝马%'
6   when @ccname='奥迪' then '%奥迪%'
7 else '%'
8 end

 

1).两者相比,Case搜索函数功能更强。

2).Case函数类似于if……else if 语句,只返回第一个符合条件的值,之后的部分会被忽略

注意:语句结束之后不要写分号或逗号

三、存储过程

1、不带参数的存储过程(跟 视图作用相同)

eg

1 create procedure MyPRO --procedure为创建存储过程关键字,也可以简写proc,MyPRO为存储过程名
2 as
3 select * from authors
4 --执行存储过程
5 exec mypro  --exec表示执行存储过程

2、带参数的存储过程

 1 create procedure BuyFriut
 2 @Uid varchar(50),
 3 @Fcode varchar(50),
 4 @Sl int
 5 as
 6 begin
 7     declare @kc int,@price float
 8     select @kc=Numbers,@price=Price from Fruit where Ids=@Fcode
 9     if @Sl>@kc
10     begin
11         print '库存不足!'
12     end
13     else
14     begin
15         declare @ye float
16         select @ye=Account from Login where UserName=@Uid
17         if @ye>= @price*@Sl
18         begin
19             update Fruit set Numbers=Numbers-@Sl where Ids=@Fcode
20             update Login set Account=Account-@price*@Sl where UserName=@Uid
21             declare @sj int
22             set @sj = cast(rand()*10000    as int)                
23             insert into Orders values(@sj,@Uid,GETDATE())--添加内容的时候 先写主键表,再写外键表
24             insert into OrderDetails values(@sj,@Fcode,@Sl)        
25         end
26         else
27         begin
28             print '余额不足!'
29             
30         end
31     end    
32 end
33 
34 go
35 --使用存储过程
36 declare @s int
37 exec  @s = BuyFriut 'wangwu','k001',20
38 print @s 
39 
40 --删除存储过程
41 drop proc BuyFriut

3、触发器

触发器是一种特殊的存储过程,只有当试图用数据操作语言DML来修改数据时才会触发,DML包含对视图和表的增、删、改。

触发器分为DML触发器和DDL触发器,其中DML触发器会对数据表,视图进行insert、update、delete的时候触发。DDL则是create、alter、drop等时触发。

DML触发器又分为after(之后触发)和insert of(之前触发)触发器。

如果在创建触发器的时候不指定类型,则默认是after触发器。

触发器有两个虚拟的临时表:插入表(inserted)和删除表(deleted),由系统在内存中创建,不会保存到数据库。并且两张表都是只读的。当触发器完成工作后,这两张表会自动删除。

增加:inserted表 记录

删除:deleted表  记录

修改:inserted表记录修改前 deleted表记录修改后

修改数据时现删掉该记录,然后再增加一天新的记录。这样inserted和updated就都存在记录了。

触发器本身就是一个事务,可以利用事务的回滚,撤销操作。事务就是要么都执行,要么一条都不执行。

创建触发器

语法:

1 create trigger [shema_name . ] trg_name
2 on { table | view }
3 [ with encryption ]
4 { for | after | instead of }
5 { insert , update , delete }
6 as
7 sql_statement

 

a、创建insert触发器

 

 1 if(object_id('tgr_test_insert','tr') is not null)
 2     drop trigger tgr_test_insert --删除触发器
 3 go
 4 create trigger tgr_test_insert
 5 on student --创建在student表
 6     for insert --insert触发
 7 as
 8 declare @id int,@name varchar(20),@sex char(2),@age int
 9 --查询inserted表中已经插入的信息
10 select @id = id,@name = name,@sex = sex, @age = age from inserted
11 --用查到的信息加入到会员表中
12 if(@age >30) --如果年龄不符合 则修改
13 begin
14     update student set age = 30 where id = @id
15     print '年龄太大,已自动修改为30'
16 end
17 insert into [user] (userName,passWord,RoleId) values (@name,@sex + cast(@age as varchar),3)
18 print '添加学生成功!';
19 print '添加会员成功!'

对student表创建触发器后对该表执行insert后

insert into student (name,sex,age,mail) values ('海盗船长','',88,'853020304@qq.com')

 

 

b、创建update触发器

 1 if(object_id('tgr_student_update','tr') is not null)
 2     drop trigger tgr_student_update
 3 go
 4 create trigger tgr_student_update
 5 on student
 6     for update
 7 as
 8     declare @oldName varchar(10),@newName varchar(10)
 9     select @oldName = name from deleted; --查找更新前的数据
10     select @newName = name from inserted;--查找更新后的数据
11     if(@oldName = @newName)
12     begin
13         print '数据相同'
14         rollback tran;   --回滚 不执行修改操作
15     end
16     else
17         print '修改成功'

 

 

update student set name='海盗船长' 

 事务在触发器中结束。批处理已中止。

update student set name='粉红娘娘'

修改成功。

c、创建delete触发器

eg

select * from Loginone
select * from biandong
go
--创建触发器
create trigger TR_LOGINONE_DELETE
on Loginone
a、for delete 触发器 --删除的时候执行(第一类)

eg1、

 

 1 create trigger TR_STUDENT_DELETE
 2 on Student
 3 as
 4 begin
 5     declare @uid varchar(50),@name varchar(50)
 6     select @uid=UserName,@name=Name from deleted
 7     insert into biandong values(@uid,@name,'删除')
 8 end
 9 
10  go
11   --在对表loginnoe进行删除的时候触发器执行
12  delete from Loginone where UserName='aaa'
13  
14  go

eg2、

if(object_id('tgr_student_delete','tr')is not null)
    drop trigger tgr_student_delete
go
create trigger tgr_student_delete
on student
    for delete
as
    if(exists(select * from sys.databases where name = 'studentBackup'))
        insert into studentBackup select name,sex,age,mail from deleted;
    else
        print '不存在,创建再插入'
        create table studentBackup
        (
            name varchar(20),
            sex char(2),
            age int,
            mail varchar(20)
        )
        insert into studentBackup select name,sex,age,mail from deleted;

 

delete from student

select * from student
select * from studentBackup

 

b、instead of delete 触发器 --替代执行(第三类)

eg1、

 1  --删除student里面的数据的时候用另外两条语句替代,先删从表再删主表
 2  
 3 create trigger TR_STUDENT_DELETE
 4  on Student
 5  instead of delete
 6 as
 7 begin
 8      declare @sno varchar(20)
 9      select @sno=sno from deleted
10      delete from score where sno=@sno
11      delete from student where sno=@sno
12 end
13  --执行删除的时候触发
14  delete from student

eg2、

if(object_id('tgr_student_inteadof','tr') is not null)
    drop trigger tgr_student_inteadof
go
create trigger tgr_student_inteadof
on student
    instead of delete -- update , insert
as
    declare @id int,@name varchar(20)
    select @id = id,@name = name from deleted;
    --instead of 先触发
    --先删除user表信息
    delete from [user] where userName = @name;
    --再删除student表信息
    delete from [student] where id = @id;

delete from student where name = '海盗船长'

 修改触发器

alter trigger tgr_test_insert
on student
for insert
as
print 'ok'

禁用触发器

disable trigger tgr_test_insert on student

启用触发器

enable trigger tgr_test_insert on student

 查询已创建的触发器

select * from sys.triggers

c、after delete --删除之后执行(第二类)

4、事务

a、开始事务 begin tran(transaction)
b、提交 commit
c、回滚 rollback

eg

 select * from Car
 select * from Brand
 
  begin transaction --开始事务
  delete from Car where Code='c005'
 delete from Brand where Brand_Code='b002'
  if @@ERROR=0--判断是否出错,如果执行没错@@ERROR为0
begin
      commit -- 提交事务
end
 else
 begin
     rollback--回滚事务
end

 --try catch
 begin transaction --开始事务
 begin try --try里面写要执行的代码
     delete from Car where Code='c005'
     delete from Brand where Brand_Code='b002'
     commit
 end try
 begin catch
     rollback
 end catch

   四、视图与存储过程的区别

视图:

    视图由SELECT查询语句所定义的一个虚拟表,是查看数据的一种非常有效的方式,同真实的数据表一样,视图也包含一系列带有名称的数据列和数据行,但视图与数据表又有很大的不同,视图中的数据并不真实的存在于数据库中。视图返回的是结果集。

存储过程:

    存储过程(Stored Procedure)是数据库系统中封装的代码模块,是一组为了完成特定功能的SQL语句集,经编译后存放在数据库服务器中,用户通过指定存储过程的名字并给出参数(如果该存储过程带有参数)来执行它。具有很好的可重用性。可以创建一个过程供永久使用,或在一个会话中临时使用(局部临时过程),或在所有会话中临时使用(全局临时程)。也可以创建在Microsoft®SQL Server™启动时自动运行的存储过程。
存储过程涉及很多的数据处理,整个是一个复杂的过程。它可以接收参数,相当于一个函数。主要目的是用来处理数据。而视图是把现在有数据组合成新的形式展示出来,其目的是用来呈现数据。

 

posted @ 2015-07-22 22:09  其实哥很宅  阅读(339)  评论(0编辑  收藏  举报