插入后在第二张表上触发更新

时间:2018-11-20 12:54:47

标签: postgresql postgresql-9.1 postgresql-9.3

我有两个表A和P。

     A
________________
id   |  num_cars
----------
1    |  2
2    |  0
3       0

             P
__________________________
id_driver    |      id_car
--------------------------
1            |    Porsche
1            |    BMW

A.id和P.id_driver指的是同一个人。我创建了以下触发器。这个想法是,每次我在P中为现有驾驶员添加新行时,其A中的对应行都必须更新为具有该ID的人所拥有的汽车总数。

CREATE OR REPLACE FUNCTION update_a() RETURNS trigger AS $$ 
BEGIN
IF TG_OP = 'INSERT' THEN
    UPDATE A a
      SET num_cars = (SELECT COUNT(NEW.id_driver)
      FROM P p
      WHERE (a.id = p.id_driver AND a.id=NEW.id_driver));
ELSIF TG_OP = 'DELETE' THEN
    UPDATE A a 
      SET num_cars = num_cars - 1
      WHERE a.id = OLD.id_driver AND a.num_cars<>0;
END IF;        
RETURN NULL;
END;
$$ LANGUAGE plpgsql;

CREATE TRIGGER add_car
AFTER INSERT OR DELETE ON PARTICIPATION
FOR EACH ROW EXECUTE PROCEDURE update_a();

当我在B中为驱动程序添加一行时,触发器工作正常。但是,如果我随后为B中的其他驱动程序添加一行,则A中的其余行都设置为0。我希望该过程仅在A.id = P.id_driver时运行。我该怎么办?

1 个答案:

答案 0 :(得分:1)

更新查询在AP之间产生叉积,因此更新整个表,大部分时间计数为0。

您将需要仅将更新限制为适当的驾驶员,并且仅计算该驾驶员的汽车数量:

UPDATE A a
SET num_cars = (SELECT COUNT(*)
      FROM P p
      WHERE p.id_driver = NEW.id_driver)
WHERE a.id = NEW.id_driver;