MySQL ONLY IN()等价子句

MySQL ONLY IN()等价子句,mysql,clause,relational-division,Mysql,Clause,Relational Division,我在这里给出了我的问题的一个非常抽象的版本,所以请容忍我。我有一个查询,它将检查一个特定的实体是否具有某些相同类型的多个参数。例如,就巧克力而言,一个男孩有多种选择。但是,我想从桌子上挑选那些吃了我提到的巧克力的男孩。不多不少,不“喜欢”或不“在() “$string”当然是一个PHP变量,它只包含那些我想用来拉男孩的巧克力的逗号分隔值 我知道这是无效的MySQL语句,但是否有任何有效的等效语句 编辑: 这是一个更全面的查询,可以在特殊情况下获取记录,但并不总是这样 SELECT boys.*

我在这里给出了我的问题的一个非常抽象的版本,所以请容忍我。我有一个查询,它将检查一个特定的实体是否具有某些相同类型的多个参数。例如,就巧克力而言,一个男孩有多种选择。但是,我想从桌子上挑选那些吃了我提到的巧克力的男孩。不多不少,不“喜欢”或不“在()

“$string”当然是一个PHP变量,它只包含那些我想用来拉男孩的巧克力的逗号分隔值

我知道这是无效的MySQL语句,但是否有任何有效的等效语句

编辑:

这是一个更全面的查询,可以在特殊情况下获取记录,但并不总是这样

SELECT boys.* FROM schools_boys INNER JOIN boys ON boys.boy_id=schools_boys.boy_id
INNER JOIN chocolates_boys a ON a.boy_id=boys.boy_id INNER JOIN schools
ON schools.school_id=schools_boys.school_id WHERE a.chocolate_id IN(1000,1003)
AND 
            EXISTS
            (
                    SELECT 1
                    FROM chocolates_boys b
                    WHERE a.boy_id=b.boy_id
                    GROUP BY boy_id
                    HAVING COUNT(DISTINCT chocolate_id) = '2'
                    )

                GROUP BY schools_boys.boy_id HAVING COUNT(*) = '2'

Boys Table
+--------+-------------+
| id     | boy         |
+--------+-------------+
| 10007  | Boy1        |
| 10008  | Boy2        |
| 10009  | Boy3        |
+--------+-------------+

Chocolates Boys Table
+----+---------+--------------+
| id | chocolate_id | boy_id |
+----+--------------+---------+
| 1  | 1000         | 10007   |
| 2  | 1003         | 10007   |
| 3  | 1006         | 10007   |
| 4  | 1000         | 10009   |
| 5  | 1001         | 10009   |
| 6  | 1005         | 10009   |
+----+--------------+---------+

当我单独选择1000来拉出两个男孩(或)1000和1003来拉出ID为10007的男孩时,不会发生任何事情。

此问题称为
关系分割

SELECT boy_id 
FROM   boys_chocolates 
WHERE  chocolate_id IN ('$string')
GROUP  BY boy_id 
HAVING COUNT(DISTINCT chocolate_id) = ? -- <<== number of chocolates specified
但是,如果每个
男孩id
巧克力id
都是唯一的,
DISTINCT
关键字是可选的

SELECT boy_id 
FROM   boys_chocolates 
WHERE  chocolate_id IN (1,2,3,4)
GROUP  BY boy_id 
HAVING COUNT(*) = 4

更新1

…我想从桌子上挑选那些吃了我提到的巧克力的男孩。不多不少…


+1回答得很好。我认为你应该去掉WHERE子句,这样你就不会返回超过所需列表中项目的男孩。实际上,这也不起作用。我认为你需要添加另一个HAVING子句,以确保它是所需的4。问题是,你将返回任何拥有这4个的男孩,无论他们是否有额外的。您应该删除WHERE子句并添加第二个HAVING子句以避免这种情况。第二个HAVING子句可以是(在您的示例中):
和COUNT(不同的情况下,当巧克力id在(1,2,3,4)中,然后巧克力id ELSE NULL END)=4
@Tom good point,我误读了这行:
…正是我提到的巧克力。请原谅,我会更新答案的。没问题。这是一个很好的回答。只是错过了那一点。
SELECT boy_id 
FROM   boys_chocolates 
WHERE  chocolate_id IN (1,2,3,4)
GROUP  BY boy_id 
HAVING COUNT(DISTINCT chocolate_id) = 4
SELECT boy_id 
FROM   boys_chocolates 
WHERE  chocolate_id IN (1,2,3,4)
GROUP  BY boy_id 
HAVING COUNT(*) = 4
SELECT boy_id 
FROM   boys_chocolates a
WHERE  chocolate_id IN (1,2,3,4) AND
        EXISTS 
        (
            SELECT  1
            FROM    boys_chocolates b
            WHERE   a.boy_ID = b.boy_ID
            GROUP   BY boy_id
            HAVING  COUNT(DISTINCT chocolate_id) = 4
        )
GROUP  BY boy_id
HAVING COUNT(*) = 4