1

当其他一些列发生变化时,我试图计算一个列上的值,所以我创建了一个这样的触发器。我的“total_points”列总是包含 0,所以有些不对劲。我做错了什么?我验证了下面的每个 SELECT 调用都返回一个非零值。

CREATE FUNCTION update_order_total_points() RETURNS trigger
  LANGUAGE plpgsql
  AS $$
BEGIN
    NEW.total_points = NEW.ud * (SELECT amount FROM points WHERE abbrev = 'ud') +
                       NEW.dp * (SELECT amount FROM points WHERE abbrev = 'dp') +
                       NEW.swrv * (SELECT amount FROM points WHERE abbrev = 'swrv') +
                       NEW.sh * (SELECT amount FROM points WHERE abbrev = 'sh') +
                       NEW.jmsw * (SELECT amount FROM points WHERE abbrev = 'jmsw') +
                       NEW.sw * (SELECT amount FROM points WHERE abbrev = 'sw') +
                       NEW.prrv * (SELECT amount FROM points WHERE abbrev = 'prrv') +
                       NEW.mhsw * (SELECT amount FROM points WHERE abbrev = 'mhsw') +
                       NEW.bmsw * (SELECT amount FROM points WHERE abbrev = 'bmsw') +
                       NEW.mp * (SELECT amount FROM points WHERE abbrev = 'mp') +
                       NEW.pr * (SELECT amount FROM points WHERE abbrev = 'pr') +
                       NEW.st * (SELECT amount FROM points WHERE abbrev = 'st');
    RETURN NEW;
END;
$$;

CREATE TRIGGER fix_total_points
AFTER INSERT OR UPDATE OF ud, dp, swrv, sh, jmsw, sw, prrv, mhsw, bmsw, mp, pr, st
ON orders
FOR EACH ROW EXECUTE PROCEDURE update_order_total_points();
4

2 回答 2

1

它正在运行AFTER INSERT,因此无法修改该行。将其设置为BEFORE触发器。

如果您能想出一种方法将这十五个左右的SELECT amount查询合并为一个,那也会使其更快。

于 2013-09-05T17:17:15.177 回答
1

这是因为当您需要 BEFORE 触发器时,您使用的是 AFTER 插入触发器。用两个触发器检查这个sql fiddle 演示;

您也可以尝试将触发器重写为这样的东西,这样您就可以从points表中选择一个:

    ...

    NEW.total_points =
        (
             with cte(amount, abbrev) as (
                 select NEW.ud, 'ud' union all
                 select NEW.dp 'dp' union all
                 select NEW.swrv, 'swrv' union all
                 ...
             )
             select sum(p.amount * t.amount)
             from points as p
                 inner join cte as t on t.abbrev = p.abbrev
        )
    ...
于 2013-09-05T17:19:51.810 回答