如何基于唯一ID计算最小采购总额?SQL聚合函数报错求助
SQL聚合函数报错解决及需求实现
场景与需求
原始数据表:
ID | UNITS_BOUGHT | UNIT_PRICE ---------------------------------- 1 | 1 | 10.99 1 | 3 | 3.49 1 | 2 | 4.99 2 | 1 | 124.99 2 | 1 | 4.99 3 | 5 | 9.99 3 | 3 | 4.99
需要完成两个目标:
- 统计表中唯一ID的总数
- 计算每个ID的采购总额(
UNITS_BOUGHT * UNIT_PRICE的求和),并找出这些总额中的最小值
期望输出:
IDs | MIN_PURCHASE -------------------- 3 | 31.44
错误代码与问题
原执行的SQL代码:
SELECT COUNT(DISTINCT ID) AS 'IDs', ROUND(MIN(SUM(UNITS_BOUGHT * UNIT_PRICE) = ( SELECT UNITS_BOUGHT * UNIT_PRICE FROM TABLE GROUP BY ID )), 2) AS 'MIN_PURCHASE' FROM TABLE;
执行后报错:invalid use of group function error(聚合函数使用无效)
错误原因
- 聚合函数嵌套非法:SQL不允许直接在一个聚合函数(如
MIN())内部嵌套另一个聚合函数(如SUM()) - 子查询逻辑错误:子查询
SELECT UNITS_BOUGHT * UNIT_PRICE FROM TABLE GROUP BY ID未对每个ID的采购额求和,分组后仅返回单条记录的乘积,不符合需求逻辑
解决方案
方案一:子查询分步计算
SELECT (SELECT COUNT(DISTINCT ID) FROM TABLE) AS IDs, ROUND(MIN(total_purchase), 2) AS MIN_PURCHASE FROM ( SELECT ID, SUM(UNITS_BOUGHT * UNIT_PRICE) AS total_purchase FROM TABLE GROUP BY ID ) AS id_purchases;
逻辑说明
- 内层子查询
id_purchases按ID分组,计算每个ID的采购总额 - 外层查询通过独立子查询获取唯一ID总数,同时对所有ID的采购总额取最小值,并用
ROUND()保留两位小数
方案二:CTE(公共表表达式)实现(适用于MySQL 8+、PostgreSQL等)
WITH id_purchases AS ( SELECT ID, SUM(UNITS_BOUGHT * UNIT_PRICE) AS total_purchase FROM TABLE GROUP BY ID ) SELECT (SELECT COUNT(*) FROM id_purchases) AS IDs, ROUND(MIN(total_purchase), 2) AS MIN_PURCHASE FROM id_purchases;
逻辑说明
- 用CTE
id_purchases预先计算每个ID的采购总额,分组后每条记录对应一个唯一ID,因此COUNT(*)即为唯一ID总数 - 直接从CTE中提取最小采购总额并格式化
内容的提问来源于stack exchange,提问作者Phoinexx
相关产品推荐
相关产品推荐

