Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/mysql/55.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Mysql 在另一个表上插入新记录时更新计数器字段_Mysql - Fatal编程技术网

Mysql 在另一个表上插入新记录时更新计数器字段

Mysql 在另一个表上插入新记录时更新计数器字段,mysql,Mysql,我有两个表,当在表B上插入或删除新记录且代码相同时,我想更新计数器记录字段表a 表A字段 ID-代码-计数器-等等 表B字段 身份证号码等 当在表B上插入/删除一条新记录时,如果它们具有相同的代码字段,我想在表a计数器字段上计算它 我想这可以用触发器来完成,但我需要一些帮助。我们可能可以用MySQL触发器来实现 我们应该考虑在“代码>表TABLE A \代码>中不存储计数器的选项,而只是从表Table B 中获得一个计数。 在实现触发器时,我们还需要注意一些问题。这可能会影响性能,对于执行DML

我有两个表,当在表B上插入或删除新记录且代码相同时,我想更新计数器记录字段表a

表A字段

ID-代码-计数器-等等

表B字段

身份证号码等

当在表B上插入/删除一条新记录时,如果它们具有相同的代码字段,我想在表a计数器字段上计算它


我想这可以用触发器来完成,但我需要一些帮助。

我们可能可以用MySQL触发器来实现

我们应该考虑在“代码>表TABLE A \代码>中不存储计数器的选项,而只是从<代码>表Table B 中获得一个计数。 在实现触发器时,我们还需要注意一些问题。这可能会影响性能,对于执行DML的触发器,可能会引入锁争用。触发器不是免费的,也不是“魔弹”

我们需要一个
AFTER UPDATE
触发器(用于处理行被更新以更改
code
列的值的情况),以及
AFTER INSERT
AFTER DELETE
触发器

我们想在表b上找到合适的索引,例如

 ON table_a (code)
假设表a
计数器
列不为空,并且
计数器
初始化为我们期望的值

作为第一个切入点:

--删除后

DELIMITER $$

CREATE TRIGGER table_b_ad
AFTER DELETE ON table_b
FOR EACH ROW
BEGIN
    -- decrement counter on row of table_a with matching OLD code
    UPDATE table_a a
       SET a.counter = a.counter - 1
     WHERE a.code <=> OLD.code
    ;
END$$

DELIMITER ;
分隔符$$
创建触发器表_b_ad
在表_b上删除后
每行
开始
--具有匹配旧代码的表_a行上的减量计数器
更新表_a
设置a.counter=a.counter-1
其中a.code.OLD.code
;
结束$$
定界符;
--插入后

DELIMITER $$

CREATE TRIGGER table_b_ai
AFTER INSERT ON table_b
FOR EACH ROW
BEGIN
    -- increment counter on row of table_a with matching NEW code
    UPDATE table_a a
       SET a.counter = a.counter + 1
     WHERE a.code <=> NEW.code
    ;
END$$

DELIMITER ;
分隔符$$
创建触发器表
在表_b上插入后
每行
开始
--表_a行上的增量计数器与匹配的新代码
更新表_a
设置a.counter=a.counter+1
其中a.code.NEW.code
;
结束$$
定界符;
--更新后

DELIMITER $$

CREATE TRIGGER table_b_au
AFTER UPDATE ON table_b
FOR EACH ROW
BEGIN
    IF NOT ( NEW.code <=> OLD.code ) THEN
       -- decrement counter on row of table_a that matches OLD code
       UPDATE table_a a
          SET a.counter = a.counter - 1
        WHERE a.code <=> OLD.code
       ;
       -- increment counter on row of table_a that matches NEW code
       UPDATE table_a a
          SET a.counter = a.counter + 1
        WHERE a.code <=> NEW.code
       ;
    END IF; 
END$$

DELIMITER ;
分隔符$$
创建触发器表
更新表_b后
每行
开始
如果不是(NEW.code OLD.code),则
--与旧代码匹配的表_a行上的减量计数器
更新表_a
设置a.counter=a.counter-1
其中a.code.OLD.code
;
--与新代码匹配的表a行上的增量计数器
更新表_a
设置a.counter=a.counter+1
其中a.code.NEW.code
;
如果结束;
结束$$
定界符;
注:

在MySQL触发器中

NEW.code
指通过INSERT或UPDATE语句分配给列
code
的“新”值

OLD.code
指UPDATE或DELETE语句之前列
code
中的“OLD”值

(spaceship运算符)是空安全比较运算符,返回TRUE或FALSE。不会像比较NULL值时常规比较运算符那样返回NULL

xy
是书写
的简写形式(x=y或(x为NULL,y为NULL))


在更新触发器中进行比较的目的是,如果
code
的值没有变化,则无需经历从该
code
值的计数中减去1,然后立即将1添加回该相同计数的繁琐过程。避免运行不必要的UPDATE语句更有效

如果遵循严格的规范化规则,则不应在表中存储计算值,而应在视图中生成计数器列。感谢@spencer7593的解决方案,还有一个问题是OLD.code和New.code的含义是什么,有不同的字段或其他内容?
NEW.
OLD.
是MySQL触发器中的特殊限定符
NEW.col
引用被插入或更新行中分配给col的“新”值,
OLD.col
引用被更新或删除行中现有“旧”值的值。(
新建。
可用于插入和更新触发器,
旧。
可用于更新和删除触发器。)