表Message已经有一个触发器.在触发器内成功运行我有一个insert声明:
Insert into tblSettlement (MessageID,Lat,Long) Select Messageid,y,x from inserted
Run Code Online (Sandbox Code Playgroud)
在桌子上tblSettlement我放置了触发器:
ALTER TRIGGER [dbo].[AddSettlementOnINSERT]
ON [dbo].[TblSettlement]
After INSERT
AS
DECLARE @id Bigint, @Lat Float,@Long Float, @LocName Varchar(200), @Dist float,@upd bit
Set @upd = (SELECT updated FROM inserted)
SET @id = (SELECT MessageID FROM inserted)
SET @lat = (SELECT [Lat] FROM inserted)
SET @Long = (SELECT [Long] FROM inserted)
if (@upd = 0)
begin
declare @table table
(Location Varchar(200),Distance float)
insert into @table
SELECT top 1 Full_Name_nd, SQRT(
POWer(69.1 * (lat - @lat), 2) +
POWer(69.1 * (@long - long) * COS(lat / 57.3), 2))As distance
FROM geodb.dbo.geonames where SQRT(
POWer(69.1 * (lat - @Lat), 2) +
POWer(69.1 * (@Long - long) * COS(lat / 57.3), 2)) < 1
set @LocName = (select location from @table)
set @Dist = (select distance from @table)
Insert into dbo.tblset2
(Messageid,lat,long,settlement,distance)values(@id,@lat,@long,@locName,@Dist)
end
Run Code Online (Sandbox Code Playgroud)
但问题是,每当我们启用上面的触发器时,插入就会停止在Message表上工作.
含义:我们希望在插入后插入几个列值并尝试在同一个表的触发器中更新另一个表.这实际上不允许我们插入.
关于SQL Server触发器的基本假设是错误的 - 您似乎假设(正如许多人所做的那样)每插入一次将触发一次触发器 - 事实并非如此!
触发器将在每个语句中调用一次 - 也就是说,如果您的语句一次插入20行,则触发器将被调用一次,伪表Inserted将包含20行.
因此,如果Inserted包含多行,则此处的语句将失败,或者选择任意随机条目:
DECLARE @id Bigint, @Lat Float,@Long Float, @LocName Varchar(200), @Dist float,@upd bit
Set @upd = (SELECT updated FROM inserted)
SET @id = (SELECT MessageID FROM inserted)
SET @lat = (SELECT [Lat] FROM inserted)
SET @Long = (SELECT [Long] FROM inserted)
Run Code Online (Sandbox Code Playgroud)
你必须完全重写你的触发器,考虑到Inserted可以并且将包含多行.
| 归档时间: |
|
| 查看次数: |
583 次 |
| 最近记录: |