【问题标题】:ANSI SQL Trigger on INSERT & UPDATE插入和更新时的 ANSI SQL 触发器
【发布时间】:2013-04-01 05:25:38
【问题描述】:

我希望编写一个符合 ANSI 的 SQL 触发器,并且相信我已经完成了 90% 的工作,但还缺少一些内容。我也对其性能(作为 SQL 语句和触发器)有一些疑问/担忧。

我有一张桌子叫widgets

widgets
widget_id   |   widget_name   |   widget_type_id   |   widget_is_fizz
========================================================================
1               Apple               1                   0
2               Kiwi                2                   0
3               Pear                3                   1
...             ...                 ...                 ...
2634            Banana              28                  0

我需要触发器在此表上发生 INSERT 或 UPDATE 时触发:

  • 对于 widget_type_id 为 17 且 widget_is_fizz 为 1 的 INSERT(真);或
  • 对于更新(出于与上述相同的原因)

当在此表上插入或更新类型 ID 为 17 的“fizz 小部件”时,我想将其 widget_name 更改为“UNKNOWN”。

到目前为止,我的最佳尝试:

CREATE TRIGGER widget_name_trigger
    ON
        widgets
    FOR
        INSERT
    AS
        UPDATE
            widgets
        SET
            widget_name = 'UNKNOWN'
        WHERE
            widget_type_id = 17
            AND
            widget_is_fizz = 1

仍然无法弄清楚如何让它对 UPDATE 执行与对 INSERT 相同的操作。也不确定它是否在语法上正确且符合 ANSI。

另外,在性能方面,有传言说我们的 DBA 讨厌触发器,当我在他面前进行代码审查时,可能会与之抗争。触发器本身就很昂贵吗?如果是这样,为什么,我可以在这里做些什么来减轻这种缓慢?提前致谢。

【问题讨论】:

  • 没有 ANSI 兼容触发器之类的东西。从理论上讲,ANSI 标准定义了“PSM 语言”来编写这样的代码,但没有一个主要的 DBMS 实现它(有些比其他更接近)。
  • 我还要向其他访问者指出,DBA 对触发器的内在关注(如果有的话)可能不是性能。例如,在“触发丰富”(笑)的环境中,维护会很快变得复杂。

标签: sql performance triggers sybase ansi-sql


【解决方案1】:

您可以对插入和更新使用相同的触发器。无需更新整个表,只需更新插入/更新的行。

CREATE TRIGGER widget_name_trigger
    ON
        widgets
    FOR
        INSERT, UPDATE
    AS
        UPDATE
            widgets
        SET
            widget_name = 'UNKNOWN'
        WHERE
            widget_type_id = 17
            AND
            widget_is_fizz = 1
            AND
            widget_id=inserted.widget_id

在性能方面:只要不引用其他表,开销就非常低。
来自 Sybase 手册:

就性能而言,触发器开销通常非常低。运行触发器所涉及的时间主要用于引用其他表,这些表可能在内存中或数据库设备上。
删除和插入的触发器测试表始终在活动内存中。触发器引用的其他表的位置决定了操作所花费的时间。

【讨论】:

猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-11-25
  • 2013-07-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多