基本的に、あなたは完全にセットベースのするとInserted
擬似テーブルに複数行で作業できるようにするには、あなたのトリガーを書き換える必要があります。
CREATE TRIGGER T
ON TABLE_2
AFTER INSERT
AS
UPDATE T1
SET bought_t = bought_t + 1
FROM TABLE_1 T1
INNER JOIN Inserted i ON i.name_t = T1.name_t
WHERE T1.bought_t < 100
がUPDATE::この作品を証明するデモ:
-- create the two tables
CREATE TABLE TABLE_2 (ID INT NOT NULL IDENTITY(1,1), ProdName VARCHAR(50))
CREATE TABLE TABLE_1 (ProdName VARCHAR(50), Bought INT)
GO
-- create trigger on "TABLE_2" to update "TABLE_1"
CREATE TRIGGER T2Insert
ON TABLE_2
AFTER INSERT
AS
UPDATE T1
SET Bought = Bought + 1
FROM TABLE_1 T1
INNER JOIN Inserted i ON T1.ProdName = i.ProdName
WHERE T1.Bought < 100
GO
-- initialize TABLE_1 with some seed data
INSERT INTO dbo.TABLE_1 (ProdName, Bought)
VALUES ('Prod1', 0), ('Prod2', 20), ('Prod3', 40), ('Prod4', 40), ('Prod100', 100)
-- insert new values into TABLE_2
INSERT INTO dbo.TABLE_2 (ProdName)
VALUES ('Prod1'), ('Prod100'), ('Prod2'), ('Prod4')
-- get data to check
SELECT * FROM dbo.TABLE_1
これは、出力をレンダリング:
- 私の意見では - このような何かをしようともそれが容易になり幸い
、
簡単に見ることができるように:挿入された
- PROD1、PROD2、Prod4も挿入された
Bought
- Prod100がない原因
Bought
の更新をした値の更新を引き起こしました
UPDATE#2:同じ値を複数同時に挿入する必要がある場合は、次のようにトリガーを少し強化する必要があります。
あなたのトリガーには、**行ごとに** **と呼ばれる**と思われる**の主な**欠陥があります。トリガは**文ごとに** **起動します。したがって、このトリガを起動させる 'INSERT'文が25行挿入された場合、トリガは一度**発生しますが、' Inserted'擬似テーブルは25行あります。あなたのコードがここで選択する25行のうちどれですか? 'SELECT @name_t = name_t FROM inserted' - 非決定論的ですが、**任意の行**を取得し、**すべての他の行を無視します**。これを考慮に入れてトリガーを書き直す必要があります。 –
これはトランザクション内にあることをどのように知っていますか? 'else into rollback'を使用すると、' insert into' TABLE_2がトランザクションで開始しなかったときに、トリガーが 'rollback'コードを実行するとエラーがスローされます。また、どのようなものがロールバックされるのかをどうやって知っていますか?他の誰かがコードを書いた場合、 'bought_t 'の値が> = 100のときに変更がロールバックされる理由を理解できますか?さらに多くの情報を必要とせずに最適化されているかどうかは言えません。まず、SSMSのトリガから 'update'文を実行し、クエリプランを取得するだけです。それはあなたに多くを伝えるべきです。 –
@marc_s確かに。 (A、B)、 ( 'B'、 'Z')、 ( 'S'、 'A')、 ( 'A'、 'B' '、' S ')、 (' D '、' G ')' と私は一度だけ実行している更新機能を持っています。 @ JamesL。 – user3832856