MySQL触发器和SUM()

时间:2015-12-04 15:33:44

标签: mysql triggers

我有两张桌子学生和家人。在学生中我有列st_income和total_income。在家庭我有收入。 Total_income是来自学生的st_income和来自family.id_student = student.id_student的家庭收入总和的总和。

我想通过触发更新total_income,我做了这个

CREATE TRIGGER family_income_update AFTER UPDATE ON `family` 
FOR EACH ROW UPDATE student SET total_income= ((SELECT SUM(income) 
FROM family WHERE family.id_student=student.id_student)+
(SELECT st_income FROM student WHERE student.id_student=NEW.id_student)) 
WHERE student.id_student=NEW.id_student 

MySQL接受了这个触发器,但是当我想更新表系列中的文件收入时,我得到了这个沟通:

1093 - 您无法指定目标表'学生'用于FROM子句

中的更新

我不知道如何解决这个问题。

更新

我试过了:

CREATE TRIGGER family_income_update AFTER UPDATE ON `family` 
FOR EACH ROW 

SET @familyIncome = SELECT SUM(income) FROM family WHERE family.id_student=student.id_student
SET @studentIncome= SELECT st_income FROM student WHERE student.id_student=NEW.id_student
SET @totalIncome=@familyIncome+@studentIncome

UPDATE student SET total_income=@totalIncome WHERE student.id_student=NEW.id_student

但我得到了这个答案:

1064 - 您的SQL语法出错;检查与您的MySQL服务器版本相对应的手册,以便使用接近' SELECT SUM(income)FROM family WHERE family.id_student = student.id_student'在第4行

更新

我尝试添加st_income的total_income值。两列都在同一个表中。我试过这个:

CREATE TRIGGER `st_income_update` AFTER UPDATE ON `student`
 FOR EACH ROW BEGIN
  UPDATE student
    SET total_income = total_income + (NEW.st_income - OLD.st_income)
    WHERE student.id_student = NEW.id_student;
END

但它会导致错误。

3 个答案:

答案 0 :(得分:1)

这就是所谓的变异表"变异表"问题。它归结为不允许行触发器访问同一个表中的其他行,因为不能保证按特定顺序更新行等等。

首先,当你需要时,你真的不应该试图存储total_income。也就是说,我认为你可以通过做像

这样的事情做你想做的事
CREATE TRIGGER family_income_update
  AFTER UPDATE ON family
  FOR EACH ROW 
BEGIN
  UPDATE student
    SET total_income = total_income + (NEW.income - OLD.income)
    WHERE student.id_student = NEW.id_student;
END;

我们的想法是相对于之前的值修改student.total_income,因为您只能相对于之前的值引用family.income

答案 1 :(得分:0)

尝试在select

中重命名学生表的别名
CREATE TRIGGER family_income_update AFTER UPDATE ON `family` 
FOR EACH ROW UPDATE student SET total_income= ((SELECT SUM(income) 
FROM family WHERE family.id_student=student.id_student)+
(SELECT b.st_income FROM student as b WHERE  b.id_student=NEW.id_student)) 
WHERE student.id_student=NEW.id_student 

答案 2 :(得分:0)

如果你在内部触发器中使用可以计算总收入的变量,然后在更新查询中使用该变量?

类似这样的事情

CREATE TRIGGER family_income_update AFTER UPDATE ON `family` 
FOR EACH ROW 

SET @totalIncome=(SELECT (st.st_income + ifnull(fam.income, 0)) as     total_income
                  FROM student st left join (
                            SELECT id_student, SUM(income) as income
                            FROM family
                            GROUP BY id_student
                        ) fam on fam.id_student = st.id_student
                  WHERE st.id_student = NEW.id_student);

UPDATE student 
SET total_income = @totalIncome 
WHERE student.id_student=NEW.id_student;