MYSQL触发器插入和更新错误: MySQL error 1241: Operand should contain 1 column(s)

标签 mysql triggers assertion

我有 4 张 table ,看起来像......

 CREATE TABLE `Faculty` (
 `FID` varchar(10) NOT NULL,
 `Name` varchar(30) NOT NULL,
 `DOB` date NOT NULL,
 `Sem` varchar(1) NOT NULL,
 `Section` varchar(1) NOT NULL,
 `Subject Code` varchar(6) NOT NULL,
 `Dep` varchar(3) NOT NULL,
 `Hours Taken` int(11) NOT NULL DEFAULT '0'
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

CREATE TABLE `Student` (
 `USN` varchar(10) NOT NULL,
 `DOB` date NOT NULL,
 `Dep` varchar(3) NOT NULL,
 `SEM` int(1) NOT NULL,
 `Class` varchar(1) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

CREATE TABLE `Student Attendance` (
`USN` varchar(10) NOT NULL,
`Subject Code` varchar(6) NOT NULL,
`Attendance` int(11) DEFAULT '0',
`Absent Days` varchar(100) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

CREATE TABLE `Subjects` (
`Subject` varchar(40) NOT NULL,
`Subject Code` varchar(6) NOT NULL,
`Dep` varchar(3) NOT NULL,
`Sem` int(1) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

现在我需要确保学生的出勤小时数(学生出勤出勤)不大于教师的出勤小时数成员(member)已为该特定科目(科目代码)修读(院系.学时)。所以我写了一个触发器来检查是否满足上述条件,以检查插入和更新。

如果小时数(学生出勤.出勤)大于我设置的学生出勤出勤 到某个字符串。我希望这能作为一个断言并给我一个错误。

CREATE TRIGGER `HoursCheckonInsert` BEFORE INSERT ON `Student 
Attendance`
FOR EACH ROW SET NEW.Attendance= IF(
( Select k.USN, s.`Subject Code`,f.`Hours Taken`,s.Attendance
   From Faculty f, `Student Attendance` s, Student k
   where s.`Subject Code` = f.`Subject Code` AND k.SEM = f.Sem AND k.Class=f.Section AND s.USN=k.USN AND 
   NEW.Attendance < f.`Hours Taken` OR NEW.Attendance = f.`Hours Taken`
 ),

NEW.Attendance,
'abcdef'
)

CREATE TRIGGER `HoursCheckonUpdate` BEFORE UPDATE ON `Student Attendance
FOR EACH ROW SET NEW.Attendance= IF(
(Select k.USN, s.`Subject Code`,f.`Hours Taken`,s.Attendance
 From Faculty f, `Student Attendance` s, Student k
 where NEW.`Subject Code`=f.`Subject Code` AND  NEW.USN=k.USN AND 
NEW.USN=s.USN AND k.SEM=f.Sem AND k.Class=f.Section AND k.DEP=f.DEP
AND (NEW.Attendance < f.`Hours Taken` OR NEW.Attendance = f.`Hours Taken`)
 ),
NEW.Attendance,
'abcdef'
 )

当我尝试将值插入学生出勤时,出现此错误:

INSERT INTO `Student Attendance` (`USN`, `Subject Code`, `Attendance`, `Absent Days`) VALUES ('1KS15BT001', '15BT44', '0', '0');

Error: 
#1241 - Operand should contain 1 column(s)

我是 MySQL 触发器的新手。

最佳答案

MySQL 的 IF() 函数需要一个标量表达式作为其第一个参数。标量表达式意味着它必须是一列,最多一行。

您使用的子查询有四列,行数未知。

从您的评论来看,您似乎只对是否有零行或多于零行匹配条件感兴趣。您是对的,如果您使用 EXISTS 谓词来测试子查询而不是在标量表达式中返回子查询的结果,那么选择什么列并不重要。

您应该使用 EXISTS 谓词来执行您想要执行的操作。请参阅https://dev.mysql.com/doc/refman/5.7/en/exists-and-not-exists-subqueries.html

CREATE TRIGGER `HoursCheckonInsert` 
BEFORE INSERT ON `Student Attendance`
FOR EACH ROW 
  SET NEW.Attendance = IF(
    EXISTS(
      SELECT *
      FROM Faculty AS f
      JOIN `Student Attendance` AS s ON s.`Subject Code` = f.`Subject Code`
      JOIN Student AS k ON k.SEM = f.Sem AND k.Class=f.Section AND k.uSN = s.USN
      WHERE NEW.Attendance <= f.`Hours Taken`),
    NEW.Attendance,
    'abcdef');

那么您将哪些列放入选择列表中实际上并不重要。我在上面展示了使用 SELECT * 的情况。没关系,因为 EXISTS 仅检查是否存在任何匹配的行,并且根本不会有结果集 - 只有 bool 值是否为零或大于零行。

您还应该使用 JOIN 语法来代替过时的逗号样式语法进行连接。我在上面的示例中展示了这一点。

关于MYSQL触发器插入和更新错误: MySQL error 1241: Operand should contain 1 column(s),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46993315/

相关文章:

php - 如何查看日期是否晚于 8 天?

sql-server - T-SQL 触发器和表名

jmeter - jmeter中是否可以自定义断言消息

c++ - OpenCv图像 block ,大小错误?

php - 从 2 个不同的表以用户或管理员身份登录

php - 我是否需要联接才能从此表中检索信息?

java - 如何根据时区在mysql中存储时间戳?

mysql - 我想要一个触发器从 MySQL 中的 2 个表中删除

mysql - Sql 触发器条件检查不起作用

未知维度的 Numpy 索引数组?