2012-03-25 10 views
2

私は研究していますが、私はそれを正しく理解できないようです。私は同じ学校でのキャリアからの()の人口を合計する必要が最初のテーブルのpopulatuonを見つけるためにSQL Server 2008のトリガー

create table school_tb 
(idSchool int identity primary key, 
nameSchool varchar(100), 
schoolPopulation int 
) 

create table career_tb 
(idCareer int identity primary key, 
nameCareer  varchar(100), 
carrerPopulation int, 
numberClasses int, 
idSchool int foreign key references school_tb(idSchool) 
) 

: は、私は次の表を持っています。 career_tbの人口を更新するときに、表school_tbの列の人口を更新するトリガーを作成する必要があります。私を助けてください。 私はこれのようなものを持っていましたが、それを働かせることはできません。

--create trigger updatePopulation 
--on career_tb 
--for update as 
--if UPDATE(carrerPopulation) 
--update school_tb set schoolPopulation =(SELECT add(carrerPopulation) 
--         from career_tb 
--         where idSchool=(SELECT idSchool 
--         from career_tb 
--         where [email protected]) 
--         ) 
--go 

何か助けていただきありがとうございます。ありがとう

+0

ところで私は、SQL Server 2008 R2 – itsmedavid

答えて

3

これはあなたを助けるはずです。トリガー本体のコメントをご覧ください。

create trigger updatePopulation 
on career_tb 
-- to update sum even if carreer gets deleted or inserted 
after insert, update, delete 
as 
-- to avoid trigger messing up rows affected 
    set nocount on 

    if UPDATE(carrerPopulation) 
    begin 
    -- update sum by difference between previous and current state of one record in career 
     update school_tb 
     set schoolPopulation = schoolPopulation + difference 
     from school_tb 
     -- derived table sums all the careers changed in one go 
     inner join 
     (
     -- sum all values from careers by school 
      select idSchool, sum (carrerPopulation) difference 
      from 
      (
       -- change sign of previous values 
       select deleted.idSchool, -deleted.carrerPopulation carrerPopulation 
        from deleted 
       union all 
       -- + current values 
       select inserted.idSchool, inserted.carrerPopulation 
        from inserted 
      ) a 
       group by idSchool 
      -- Skip update in case of no change 
       having sum (carrerPopulation) <> 0 
     ) a 
      on school_tb.idSchool = a.idSchool 
    end 
+0

ハローを使用しています。ありがとう。あなたの答えをしようとしていますが、まだ削除されて挿入された値を選択する前に選択肢で動作していない、無効な列名を言っています:私は本当にあなたの答えをありがとう。ありがとうございます。 – itsmedavid

+0

私の回答が少し変わりました。もう一度お試しください。 –

+0

私は今これを取得していますメッセージ8155、レベル16、状態2、プロシージャupdatePopulation、行30 'a'の列2に列名が指定されていません。 メッセージ167、レベル16、状態1、プロシージャupdatePopulation、行32 無効な列名 'carrerPopulation'。 メッセージ207、レベル16、状態1、プロシージャupdatePopulation、行19 無効な列名 'carrerPopulation'。 – itsmedavid

2
CREATE TRIGGER name ON career_tb 
AFTER INSERT, UPDATE, DELETE 
AS 
BEGIN 
    SET NOCOUNT ON; 

    MERGE school_tb T 
    USING 
    (
     SELECT idSchool, SUM(carrerPopulation) res 
     FROM 
     (
      SELECT idSchool, carrerPopulation 
      FROM INSERTED 
      UNION ALL 
      SELECT idSchool, -carrerPopulation 
      FROM DELETED 
     ) t 
     GROUP BY idSchool 
    ) S 
    ON T.idSchool = S.idSchool 
    WHEN MATCHED THEN UPDATE SET 
     schoolPopulation = T.schoolPopulation +S.res 
    ; 


END 
+0

私はコード化してみましたが、「後ろの」構文が間違っていると言いますが、それを取り除こうとしましたが、 'それは存在しないか無効です(そして存在します)それを感謝します – itsmedavid

+0

こんにちは。私はあなたの答えに 'update(poblacion)'と次のコードを追加してトリガーを作成することができましたが、schoolPopulationの値をクレイジーな数字で更新しています。たとえば、あるキャリアを1000キャリアに更新したときに-9990とします.Population – itsmedavid

+0

@itsmedavid訂正されました。もしあなたが 'If update(population)'を取り除いて、削除時に確実に動作するかチェックしてください。 –