如何在第三个查询中包含来自其他两个表的过滤行数?

Posted

技术标签:

【中文标题】如何在第三个查询中包含来自其他两个表的过滤行数?【英文标题】:How do I include filtered rowcounts from two other tables in a query of a third? 【发布时间】:2009-01-22 02:55:01 【问题描述】:

我有一个 mysql 数据库,其中包含三个需要在查询中组合的表:计划、注册和候补名单。他们正在实施一个基本的班级注册系统。

Schedule 包含已安排的课程。当用户注册课程时,他们的用户帐户 id 和预定课程的 id 存储在注册中。如果某个班级已满员,则将它们存储在候补名单中。这三个表共享一个 scheduleId 列,用于标识每个类。

当我查询日程表时,我还需要返回已注册和等待列表列,这些列表示已注册并等待特定 scheduleId 的用户数。

我想出的一个初步查询是:

select s.id, s.classDate, s.instructor, COUNT(e.id) as enrolled
from schedule as s
left outer join enrolled as e
on s.id = e.scheduleId
group by s.id

其中一个都可以,但显然我无法以这种方式获取已注册和候补表的值。 任何人都可以提出一个好的方法吗?

【问题讨论】:

【参考方案1】:

使用嵌套的 SELECT 查询。假设您的架构有一点点,像这样的东西怎么样(可能不适用于某些 SQL 风格):

select s.id, s.classDate, s.instructor, 
       (select COUNT(e.id) from enrolled e where e.scheduleId = s.id) as enrolled,
       (select COUNT(w.id) from waitlist w where w.scheduleId = s.id) as waiting
from schedule as s
group by s.id

【讨论】:

【参考方案2】:

我会用另一个左连接和两个内联计数(不同)

select s.id, s.classDate, s.instructor ,
count(distinct e.id) as enrolled,
count(distinct w.id) as waiting
from schedule as s
left outer join enrolled as e
on s.id = e.scheduleID
left outer join waitlist as w
on s.id = w.scheduleID
group by s.id

当我运行这种方法与子查询相比时,它的执行速度大约是它的两倍,但我正在查看一个非常小的结果集。

【讨论】:

【参考方案3】:

两种快捷方式:

1- 使用COUNT(DISTINCT e.id), COUNT(DISTINCT w.id) 获取每个表中唯一实例的数量,然后加入两者。这可能是非常低效的。

2- 在FROM 子句中使用子查询(仅适用于 MySQL 5.0 及更高版本):

SELECT s.id, s.classDate, s.instructor, tmpE.c AS enrolled, tmpW.c AS waiting
FROM
  schedule AS s,
  ( SELECT scheduleID, COUNT(*) AS c FROM enrolled GROUP BY scheduleID ) AS tmpE,
  ( SELECT scheduleID, COUNT(*) AS c FROM waiting GROUP BY scheduleID ) AS tmpW
WHERE
    s.id = e.scheduleID
    AND s.id = w.scheduleID
GROUP BY s.id

不过,我可能错过了那里的左连接。

【讨论】:

以上是关于如何在第三个查询中包含来自其他两个表的过滤行数?的主要内容,如果未能解决你的问题,请参考以下文章

如何过滤 FK 中包含的对象?

如何在 django 中包含条件 order_by?

excel中的数据交集

linux输出文件中包含某个字符串的行数

SQL如何查询出某一列中不同值出现的次数?

如何在 obiee 的左外连接的一部分中包含分析过滤器(左连接变为内连接)