sql - PostgreSQL 中的 "Reference counting"触发器

标签 sql postgresql triggers reference-counting referential-integrity

给定一个包含下表的 postgreSQL 查询:

+--------------------+
|Foo                 |
+--------------------+
| id | value1 | refe |
+--------------------+

+--------------------+
|Bar                 |
+--------------------+
| id | value2 | refe |
+--------------------+

+-------------+
|Refe         |
+-------------+
| id | value3 |
+-------------+

其中 refe 列是 Refeid 的外键。现在 Refe 存储与 FooBar(以及可能的其他表)相关的附加数据。

我创建了一个 View 来存储“事件的”refe,换句话说:Foorefe 字段的联合> 和 条形图:

CREATE OR REPLACE VIEW liverefe AS 
        (SELECT refe FROM Foo)
        UNION (SELECT refe FROM Bar)

现在,当从 FooBar 中删除一行时,refe 有可能失效(没有其他 FooBar 行引用它)。在这种情况下,它应该被删除。

可以解释一下如何实现这种“引用计数”触发器吗?

最佳答案

使用NOT EXISTS反半连接。

删除refe中的所有死行:

DELETE FROM refe r
WHERE NOT EXISTS (SELECT 1 FROM foo WHERE refe = r.id)
AND   NOT EXISTS (SELECT 1 FROM bar WHERE refe = r.id);

(可能)在其中一个引用表中的 DELETE/UPDATE 之后从 refe 中删除特定行:

DELETE FROM refe r
WHERE r.id = 12345   -- your id here
AND   NOT EXISTS (SELECT 1 FROM foo WHERE refe = r.id)
AND   NOT EXISTS (SELECT 1 FROM bar WHERE refe = r.id);

带有此类触发器的完整代码示例的相关答案:

如果您有更新 refe 列的习惯,请添加如下触发器:

CREATE TRIGGER foo_updelaft_kill_orphaned_refe
AFTER DELETE <b>OR UPDATE OF refe</b>
ON foo
FOR EACH ROW EXECUTE PROCEDURE f_trg_kill_orphaned_refe();

同样适用于表 bar
这样,仅当 UPDATE 实际针对 refe 列时才会调用触发器。

Details in the manual.

关于sql - PostgreSQL 中的 "Reference counting"触发器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25184726/

相关文章:

java - PostgreSQL 和 hibernate - 函数 rownumber() 不存在

mysql - 在 INSERT ON DUPLICATE 语句期间以什么顺序调用 mysql 触发器?

java - ClassNotFoundException 和 NPE 同时出现

mysql - 将数据插入有条件的表中的每条记录中,但自动填充它......我会尽力解释 :-)

c# - 是否可以在 linq to Entity Framework 中选择一个字符串?

postgresql - DataGrip 无法连接到在具有 WSL2 后端的 Windows Docker Desktop 中运行的本地 PostgreSQL

postgresql - Postgres 内存值得一试吗?

sql - Oracle 创建触发器语句失败并出现内部错误代码 ORA-00600

mysql 触发器 - 从触发器中选择计数(*)

sql - 复合 PK 部分的外键