选择具有相同外键但另一列具有一组值的行

时间:2019-06-17 18:24:08

标签: mysql sql

我设计了一个数据库,该数据库以这种格式存储数据,其中两列都是通向不同表的外键。这是简化版。

RNA_id | Experiment_id |
   1   |       a       |
   1   |       b       |
   2   |       a       |
   2   |       b       |
   2   |       c       |
   3   |       b       |
   4   |       a       |
   4   |       c       |

我想选择具有所有三个实验ID的行。在此示例中,结果应为

RNA_id | Experiment_id |
   2   |       a       |
   2   |       b       |
   2   |       c       |

我尝试了

GROUP BY RNA_id HAVING COUNT (DISTINCT Experiment_id)=3

但这只是导致我的行看似随机的分类。

数据库已经很大,我的查询已经相当复杂,此外,我可能希望扩展到4个或更多的Experiment_id。

这是我查询的清理版本,因为它很复杂,我不想解释我的整个数据结构

我现有的查询是:

SELECT RNA_id, Experiment_id, <data values>
FROM data
LEFT JOIN ref1
LEFT JOIN ref2
LEFT JOIN ref3
LEFT JOIN ref4
WHERE <required data parameters>
ORDER BY RNA_id
LIMIT 0,5000;

应返回大约700个值, 但是当我较早地将ORDER BY更改为该GROUP BY命令时,它将返回9个值,所有这些值均具有唯一的RNA_id,并且应该返回大约100个。

我的RNA_id实际上是3列,所以我可能只需要重做整个数据库就可以使用这些解决方案。

我的解决方案

我弄清楚了如何使用3列标识符

AND (RNA_id1, RNA_id2, RNA_id3) IN (SELECT RNA_id1, RNA_id2, RNA_id3
FROM data
WHERE <parameter>
GROUP BY RNA_id1, RNA_id2, RNA_id3
HAVING COUNT (DISTINCT Experiment_id)=3)

这也适用于不同数量的Experiment_ids

3 个答案:

答案 0 :(得分:1)

我建议只返回同时具有全部三个的RNA_id

select RNA_id
from t
where Experiment_id in ('a', 'b', 'c')
group by RNA_id
having count(*) = 3;

如果可以重复,请使用count(distinct experiment_id)

如果您想要原始行,那么在MySQL 8+中,您可以使用窗口函数对此进行调整:

select t.*
from (select t.*, count(*) over (partition by RNA_id) as cnt
      from t
      where Experiment_id in ('a', 'b', 'c')
     ) t
where cnt = 3;

答案 1 :(得分:1)

SQL DEMO

SELECT *
FROM Table1 t1
WHERE ( SELECT COUNT(DISTINCT `Experiment_id`)
        FROM Table1 t2
        WHERE t2.`RNA_id` = t1.`RNA_id`
          AND t2.Experiment_id in ('a', 'b', 'c') -- if you have more than 3 experiment
      )  = 3

答案 2 :(得分:1)

如果abcExperiment_id的唯一可能值,那么您需要像下面这样将查询放在WHERE子句中:

select *
from tablename
where RNA_id in (
  select RNA_id from tablename
  group by RNA_id
  having count(distinct Experiment_id) = 3
)

如果还有其他值:

select *
from tablename
where
  Experiment_id in ('a', 'b', 'c') 
  and RNA_id in (
  select RNA_id from tablename
  where Experiment_id in ('a', 'b', 'c')
  group by RNA_id
  having count(distinct Experiment_id) = 3  
)

如果要扩展到三个以上的值,可以轻松更改这些查询。