题解 | 返回每个顾客不同订单的总金额

返回每个顾客不同订单的总金额

https://www.nowcoder.com/practice/ce313253a81c4947b20e801cd4da7894

思路分析:

题目需要返回每个顾客的cust_id以及他们订购的订单总金额,可以看到每一个顾客都对应一个order_num,在OrderItems表中有订单信息,将相同order_num的记录聚合到一起,将这些记录对应的item_price * price加总,就是这个order_num的总的订单金额,也就是这个order_num所对应的cust_id的订单金额。可以看到数据涉及两个表之间的联动,两种方式,一种使用表连接,另外一种使用关联标量子查询。

代码解释:

方法一:表连接

SELECT
    cust_id,
    total_ordered
FROM
    Orders
JOIN
    (
        SELECT
            order_num,
            SUM(item_price * quantity) AS total_ordered
        FROM
            OrderItems
        GROUP BY
            order_num
    ) AS total
ON
    Orders.order_num = total.order_num
ORDER BY
    total_ordered DESC;

将Orders表和一张临时表连接,在临时表中进行分组聚合,计算每个order_num的总金额,通过order_num相等使两表连接,最后选择cust_id和total_ordered即可。

方法二:关联标量子查询

SELECT
    cust_id,
    (
        SELECT
            SUM(item_price * quantity)
        FROM
            OrderItems
        WHERE
            OrderItems.order_num = Orders.order_num
    ) AS total_ordered
FROM
    Orders
ORDER BY
    total_ordered DESC;

不需要连接,仅从Orders表中查询,在SELECT子句中直接嵌入子查询,形成一个新列,该子查询依赖于主查询提供的记录数据,针对主查询的每一条记录,返回单个值,因此属于关联标量子查询。整体的执行过程是:主查询依次遍历Orders表中的每一条记录,每遍历一条,就执行一次子查询,主查询首先抽取出第一条记录,获得一个Orders.order_num数据,子查询执行,进入OrderItems表中,查找表中OrderItems.order_num等于主查询中抽取出的这条Orders.order_num记录,针对这些记录求SUM(item_price * quantity),即求出该order_num的总金额,返回给主查询作为新列的第一行数据,接着主查询遍历Orders表中第二条记录,再次进入子查询执行,以此类推,当主查询遍历完所有记录,新列每一行的数据也就都有了,整个查询结束。可以看到使用这样的方式不需要GROUP BY分组,因为在子查询中的WHERE OrderItems.order_num = Orders.order_num是根据主查询的每一条记录到子查询的表中去筛选的,就相当于起到了分组的效果。最后子查询是直接作为新列的,因此赋予列名total_ordered。

两种方式的比较:

两种方法在结果上是相同的,但关联标量子查询采用的是循环嵌套的执行逻辑,当遇到表中数据量很大的情况时,关联标量子查询的效率可能不如表连接,实际场景中更推荐使用表连接的方式。

全部评论

相关推荐

评论
点赞
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务