MySQL IN()运算符不工作

时间:2014-05-12 21:31:01

标签: mysql sql mysqli mysql-select-db

如何使用IN()运算符不能正常工作。

这些表是示例,看起来与我拥有的真实数据库相同。我没有允许添加表格或更改

这些是表格:

students
+------+------+
| id   | name |
+------+------+
|    1 | ali  |
|    2 | man  |
|    3 | sos  |
+------+------+

Classes
+------+---------+
| c_id | students|
+------+---------+
|    1 | 1,2,3,4 |
|    2 | 88,33,55|
|    3 | 45,23,72|
+------+---------+

当我使用此查询时,它只返回id为1的学生 因为“ id IN(学生)”在第一个值相等时返回1。

select name,c_id from students,classes where id IN (students);

当我在PHP上获取列表而不是添加它。它工作正常。但是,这个解决方案需要一个循环并且需要花费很多查询。

select name,c_id from students,classes where id IN (1,2,3,4);
  

FIND_IN_SET()

同样的情况发生,它只返回1,但如果其他位置的值返回0。

3 个答案:

答案 0 :(得分:4)

IN运算符运行正常,适用于它的功能。

首先,考虑重组数据以进行规范化,并避免将值存储为逗号分隔列表。

其次,如果您必须处理包含逗号分隔值列表的列,MySQL会提供 FIND_IN_SET() 函数。


<强>后续

抛弃连接操作的旧式逗号语法,改为使用JOIN关键字。并将连接谓词从WHERE子句重定位到ON子句。完全限定列引用,例如

SELECT s.name
     , c.c_id
  FROM students s
  JOIN classes c
    ON FIND_IN_SET(s.student_id,c.students)
 ORDER BY s.name, c.c_id

重申一下,存储一个以逗号分隔的列表&#34;在列中是反模式;它反对关系理论和规范化,并忽视关系数据库的最佳实践。 0

有人可能会争取提高性能,但这种模式并没有提高性能;相反,它会增加查询和DML操作的不必要的复杂性。

答案 1 :(得分:2)

你需要三张桌子。 一个表格students,一个表格classes,然后是一个表格,例如students_to_classes包含类似

的内容
c_id | student_id
1    | 1
1    | 2
1    | 3
1    | 4
2    | 88

等等。 然后你可以查询

select c_id from students_to_classes where student_id in (1,2,3,4)

Google“n:m relationship”的背景知识。

修改

我知道你不是专门要求另一个表结构,但这是一种使用IN的数据类型(单个数字)的方法。请相信我这是正确的方法,你遇到像IN这样简单的问题的原因是你使用的是非标准的方法,对于这样的标准问题,通常不是一个好主意。

答案 2 :(得分:0)

这不是函数IN应该如何工作。如果您有可能的匹配列表,请使用IN:

而不是:

WHERE id=1 or id=2 or id=3 or id=4

你使用:

WHERE id IN (1,2,3,4)

无论如何,你的逻辑不正确。 Class和Student的关系是多对多的,因此需要第三个表。我们称之为studend_class,您可以在其中存储每个班级的学生。

student
+------+------+
| id   | name |
+------+------+
|    1 | ali  |
|    2 | man  |
|    3 | sos  |
+------+------+

class
+------+---------+
|  id  |  name   |
+------+---------+
|    1 | math    |
|    2 | english |
|    3 | science |
+------+---------+

student_class
+------------+-------------+
|  class_id  |  student_id |
+------------+-------------+
|          1 |           1 |
|          1 |           2 |
|          1 |           3 |
|          3 |           3 |
+--------------+-----------+

在上面的例子中,所有学生都在数学课上,而阿里也在科学课上。

最后,如果你想知道哪些学生在哪个班级,让我们说数学,你可以使用:

SELECT s.id, s.name, c.name
FROM student s
INNER JOIN student_class sc ON sc.student_id=s.id
INNER JOIN class c ON sc.class_id = c.id
WHERE c.name="math";