我有一个触发器" 更新后"在我的表格中,但我需要知道列如何更改。 我不想这样做:
IF OLD.*column* <> NEW.*column* THEN ...
有人有诀窍吗?
答案 0 :(得分:3)
没有技巧。如果要检测列的值是否已更改,则需要明确比较OLD.col
和NEW.col
的值。
SQL的一个怪癖是三值布尔逻辑。对NULL值的不等式测试永远不会返回TRUE。 (在布尔上下文中计算的表达式可以返回以下三个值之一:TRUE
,FALSE
或NULL
。
foo <> NULL --> NULL
NULL <> NULL --> NULL
foo <> bar --> TRUE
如果要检测列的值是否已更改,包括更改为NULL值还是从NULL值更改,则不等式测试不会将其删除。
一个技巧是使用零安全比较运算符(太空船符号 <=>
),它将仅返回TRUE或FALSE,即使被比较的一个或两个值都是NULL,检测差异:
IF NOT (NEW.col <=> OLD.col) THEN
-- value of col was modified
END IF;
另一个技巧是使用SQL语句来帮助生成触发器主体中需要的一些代码。引用columns
数据库中的information_schema
表。这是一个简短的示例,但可以扩展为包含其他语句和END IF
。从中返回可以粘贴到文本编辑器中,以帮助您构建触发器主体。
SELECT CONCAT(' IF NOT (NEW.`',c.column_name,'` <=> OLD.`',c.column_name,'`) THEN') AS i
FROM information_schema.columns c
WHERE c.table_name = 'mytable'
AND c.table_schema = 'mydatabase'
ORDER BY c.ordinal_position
返回类似
的内容--------------------------------------------------------------
IF NOT (NEW.`id` <=> OLD.`id`) THEN
IF NOT (NEW.`created` <=> OLD.`created`) THEN
IF NOT (NEW.`display_name` <=> OLD.`display_name`) THEN
如果你有很多专栏,这会非常有用。
除此之外,还没有任何其他&#34;技巧&#34;。