MS SQL 触发器问题

mlmary 2003-08-21 10:35:14
两个表结构相同——

CREATE TABLE [test] (
[id] [int] IDENTITY (1, 1) NOT NULL ,
[姓名] [varchar] (8) COLLATE Chinese_PRC_CI_AS NULL ,
[年龄] [int] NULL ,
CONSTRAINT [PK_test] PRIMARY KEY CLUSTERED
(
[id]
) ON [PRIMARY]
) ON [PRIMARY]
GO

CREATE TABLE [tests] (
[id] [int] IDENTITY (1, 1) NOT NULL ,
[姓名] [varchar] (8) COLLATE Chinese_PRC_CI_AS NULL ,
[年龄] [int] NULL ,
CONSTRAINT [PK_tests] PRIMARY KEY CLUSTERED
(
[id]
) ON [PRIMARY]
) ON [PRIMARY]
GO


PS:两个表仅是做实验用,就别问俺“为啥建两个相同表”了

数据也相同

姓名 年龄
----------------------
张三 1
李四 2
王五 3
赵六 4


在test表上建触发器

CREATE TRIGGER testtri ON dbo.test
FOR UPDATE
AS
update tests set
姓名=inserted.姓名,
年龄=inserted.年龄
from tests,deleted,inserted
where tests.姓名=deleted.姓名


问题来了——

执行
update test set 年龄=年龄+1 where 姓名='张三'
不会有问题,tests表中的张三的年龄可以变

但是,如果执行
update test set 年龄=年龄+1
就惨了,tests表中的四行数据全都变成赵六的了

为什么呀?是我对触发器理解错了吗?
请大家帮忙指点指点吧,谢谢
...全文
37 9 打赏 收藏 转发到动态 举报
写回复
用AI写文章
9 条回复
切换为时间正序
请发表友善的回复…
发表回复
chenqinzeng 2003-08-22
  • 打赏
  • 举报
回复
这个也是很容易的,编写触发器的时候deleted是存放删除掉的记录和修改过旧的记录,而inserted是存放新增加的数据和修改过新的数据,这下你应该可以自己搞定了吧
mlmary 2003-08-21
  • 打赏
  • 举报
回复
为什么 chenqinzeng(chenqinzeng) 和 happy_0325(快乐) 都要使用 “where tests.姓名=inserted.姓名”呢

如果这样写的话,执行update test set 姓名=姓名 + '人'的话,就不对了

happy_0325 2003-08-21
  • 打赏
  • 举报
回复
CREATE TRIGGER testtri ON dbo.test
FOR UPDATE
AS
update tests set
姓名=inserted.姓名,
年龄=inserted.年龄
from tests,inserted
where tests.姓名=inserted.姓名
mlmary 2003-08-21
  • 打赏
  • 举报
回复
where tests.姓名=inserted.姓名
?
但是如果我update了姓名的值的话这样就会出错呀?
chenqinzeng 2003-08-21
  • 打赏
  • 举报
回复
在test表上建触发器

CREATE TRIGGER testtri ON dbo.test
FOR UPDATE
AS
update tests set
姓名=inserted.姓名,
年龄=inserted.年龄
from tests,deleted,inserted
where tests.姓名=inserted.姓名


就行了,因为update test set 年龄=年龄+1执行之后
表deleted内容如下:
张三 1
李四 2
王五 3
赵六 4
表inserted内容如下:
张三 2
李四 3
王五 4
赵六 5

mlmary 2003-08-21
  • 打赏
  • 举报
回复
大力大大,可以不用ID这个字段吗?
为什么用tests.姓名=deleted.姓名不行呢?
pengdali 2003-08-21
  • 打赏
  • 举报
回复
CREATE TABLE [test] (
[id] [int] IDENTITY (1, 1) NOT NULL ,
[姓名] [varchar] (8) COLLATE Chinese_PRC_CI_AS NULL ,
[年龄] [int] NULL ,
CONSTRAINT [PK_test] PRIMARY KEY CLUSTERED
(
[id]
)
)
GO

CREATE TABLE [tests] (
[id] [int] ,
[姓名] [varchar] (8) COLLATE Chinese_PRC_CI_AS NULL ,
[年龄] [int] NULL ,
CONSTRAINT [PK_tests] PRIMARY KEY CLUSTERED
(
[id]
),
FOREIGN KEY (FK_ID) REFERENCES test (id)
)
GO



CREATE TRIGGER testtri ON dbo.test
FOR UPDATE
AS
update tests set 姓名=inserted.姓名, 年龄=inserted.年龄 from inserted where tests.id=inserted.id
go
helodd 2003-08-21
  • 打赏
  • 举报
回复
你都没有条件,肯定update 所有的.
update test set 年龄=年龄+1
where 姓名 in select 姓名 from inserted
aierong 2003-08-21
  • 打赏
  • 举报
回复
up
实验四 存储过程、触发器与索引 一、实验目的 1.熟悉大型数据库实验环境,以MS SQL SERVER为例; 2.掌握视图; 3.掌握存储过程与触发器; 4.掌握MS SQL SERVER的导入和导出; 5.掌握MS SQL SERVER的索引。 二、实验内容 (1)使用“实验一”中的数据库“abc”,创建一个视图,生产厂家为“北京”且价格低于北京生产的产品的平均价格,输出产品的名称、价格和生产厂家。 (2)使用“实验一”中的数据库“abc”,创建一个带有输入参数的存储过程proc_abc,查询指定职工的销售记录,用户输入职工编号,存储过程返回职工名称、产品名称、销售日期、销售数量,假如执行存储过程时所提供的“职工编号”不存在,存储过程应给予一定的提示。 (3)使用“实验一”中的数据库“abc”,练习使用游标, 写出按如下报表形式显示结果的SQL语句,该报表查询每年每种产品总销售金额,(总销售金额=价格*销量),报表显示格式如下所示: 年 产品号 产品名 销售总量 总销售金额(万元) 2001年 2 AAA 590 3.2 2001年 5 BBB 644 23.3 2002年 1 CCC 32 0.2 (4)使用“实验一”中的数据库“abc”,练习使用触发器,在销售表上创建触发器tr_updateprice,每次新增销售记录时,自动更新产品表的单价,更新方法是:每增加一笔销售记录,就将该产品的单价减去1块钱。 (5)将100万行网络连接监控数据Netflow导入数据库,创建多个索引,观察创建索引对数据库文件大小的影响;并设计不同的查询语句来观察索引对查询效率的影响;可以尝试将100万行记录扩展为1000万行,然后再做索引和查询的实验?文件见附件。

34,576

社区成员

发帖
与我相关
我的任务
社区描述
MS-SQL Server相关内容讨论专区
社区管理员
  • 基础类社区
  • 二月十六
  • 卖水果的net
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧