聚合 MySQL 函数总是返回单行吗?

问题描述 投票:0回答:1

例如,我有一个查询,需要返回包含某些数据的所有行以及包含其中一列总数的另一列。如果事情按我的预期进行,它会看起来像:

 SELECT
 order_id,
 cost,
 part_id,
 SUM(cost) AS total
 FROM orders 
 WHERE order_date BETWEEN xxx AND yyy

我会得到我的订单的所有行,并将总数附加到每行的末尾。我知道每次总数都是相同的,但这是预期的。现在为了让它发挥作用,我正在使用:

 SELECT
 order_id,
 cost,
 part_id,
 (SELECT SUM(cost)
 FROM orders
 WHERE order_date BETWEEN xxx AND yyy) AS total
 FROM orders 
 WHERE order_date BETWEEN xxx AND yyy

本质上运行相同的查询两次,一次用于总计,一次用于其他数据。但如果我想要求和,以及我不知道的平均成本,那么我就会执行相同的查询 3 次,这似乎是错误的。

非常感谢任何帮助。

mysql database sum aggregate-functions
1个回答
7
投票

您需要使用

GROUP BY
来获得您想要的结果:

SELECT
order_id,
part_id,
SUM(cost) AS total
FROM orders 
WHERE order_date BETWEEN xxx AND yyy
GROUP BY order_id, part_id

这将对您的结果进行分组。请注意,由于我假设

order_id
part_id
是复合 PK,因此上面的
SUM(cost)
可能会是
= cost
(因为您通过保证唯一的两个字段的组合进行分组。相关的下面的子查询将克服这个限制)。

获取的任何非聚合行都需要在

GROUP BY
行中指定。

有关更多信息,您可以在此处阅读有关

GROUP BY
的教程:

MySQL 教程 - 分组依据


编辑:如果您想将列用作聚合和非聚合,或者如果您需要取消分组的隔离,则需要使用子查询,如下所示:

SELECT
or1.order_id,
or1.cost,
or1.part_id,
(
  SELECT SUM(cost)
  FROM orders or2
  WHERE or1.order_id = or2.order_id
  GROUP BY or2.order_id
) AS total
FROM orders or1
WHERE or1.order_date BETWEEN xxx AND yyy
© www.soinside.com 2019 - 2024. All rights reserved.