【问题标题】:SQL one-to-many match the one side by ALL in many sideSQL 一对多在多方面通过 ALL 匹配一方面
【发布时间】:2008-10-16 18:50:49
【问题描述】:

下面一对多

CREATE TABLE source(id int, name varchar(10), PRIMARY KEY(id));
CREATE TABLE params(id int, source int, value int);

其中 params.source 是 source.id 的外键

INSERT INTO source values(1, 'yes');
INSERT INTO source values(2, 'no');

INSERT INTO params VALUES(1,1,1);
INSERT INTO params VALUES(2,1,2);
INSERT INTO params VALUES(3,1,3);

INSERT INTO params VALUES(4,2,1);
INSERT INTO params VALUES(5,2,3);
INSERT INTO params VALUES(6,2,4);

如果我有一个参数值列表(例如 [1,2,3]),我如何在 SQL 中找到具有列表中所有值的所有源(源 1,“是”)?

谢谢

【问题讨论】:

  • 我希望其他人比我更了解这一点……您可能需要考虑重新措辞。

标签: sql sql-match-all


【解决方案1】:
SELECT s.*
FROM source AS s
 JOIN params AS p ON (p.source = s.id)
WHERE p.value IN (1,2,3)
GROUP BY s.id
HAVING COUNT(DISTINCT p.value) = 3;

您需要 DISTINCT,因为不会阻止您的 params.value 重复。

【讨论】:

  • 这是最优雅的,在 lassevk 实现相同之前 :)
【解决方案2】:

编辑已修改以处理给定源的值可能多次出现的情况。

试试这个:

SELECT
    *
FROM
    source
WHERE
    (
        SELECT COUNT(DISTINCT value)
        FROM params
        WHERE params.source = source.id
          AND params.value IN (1, 2, 3)
    ) = 3

您也可以将其重写为 GROUP BY:

SELECT
    source.*
FROM
    source
    INNER JOIN params ON params.source = source.id
WHERE
    params.value IN (1, 2, 3)
GROUP BY
    source.id,
    source.name
HAVING
    COUNT(DISTINCT params.value) = 3

【讨论】:

  • 我肯定会按语法去组。更具表现力,看起来更不痛苦。
  • 如果 params 中有不止一条记录,同一来源的值相同?
  • 这是一个很好的问题拉斯。我想詹姆斯需要告诉我们这是否属实。
  • 嗯,DISTINCT 从来都不是我对任何事情的第一个解决方案,在他的情况下,我见过很多次的设置,不止一次具有相同的值是非典型的。但我已经相应地修改了解决方案。
  • 如果您知道 params 表中不同值的数量,您可以在上面的 WHERE 子句中删除 params.values IN (1,2,3),也许使用 int 变量来匹配不同的计数反对
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2022-01-18
  • 2011-11-02
  • 2016-08-06
  • 2018-01-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多