傳送門:1084. 銷售分析 III
題目
表: Product
±-------------±--------+
| Column Name | Type |
±-------------±--------+
| product_id | int |
| product_name | varchar |
| unit_price | int |
±-------------±--------+
product_id 是該表的主鍵(具有唯一值的列)。
該表的每一行顯示每個產品的名稱和價格。
表:Sales
±------------±--------+
| Column Name | Type |
±------------±--------+
| seller_id | int |
| product_id | int |
| buyer_id | int |
| sale_date | date |
| quantity | int |
| price | int |
±----- ------±--------+
這個表可能有重復的行。
product_id 是 Product 表的外鍵(reference 列)。
該表的每一行包含關于一個銷售的一些信息。
編寫解決方案,報告 2019年春季 才售出的產品。即 僅 在 2019-01-01 (含)至 2019-03-31 (含)之間出售的商品。
以 任意順序 返回結果表。
結果格式如下所示。
示例 1:
輸入:
Product table:
±-----------±-------------±-----------+
| product_id | product_name | unit_price |
±-----------±-------------±-----------+
| 1 | S8 | 1000 |
| 2 | G4 | 800 |
| 3 | iPhone | 1400 |
±-----------±-------------±-----------+
Sales table:
±----------±-----------±---------±-----------±---------±------+
| seller_id | product_id | buyer_id | sale_date | quantity | price |
±----------±-----------±---------±-----------±---------±------+
| 1 | 1 | 1 | 2019-01-21 | 2 | 2000 |
| 1 | 2 | 2 | 2019-02-17 | 1 | 800 |
| 2 | 2 | 3 | 2019-06-02 | 1 | 800 |
| 3 | 3 | 4 | 2019-05-13 | 2 | 2800 |
±----------±-----------±---------±-----------±---------±------+
輸出:
±------------±-------------+
| product_id | product_name |
±------------±-------------+
| 1 | S8 |
±------------±-------------+
解釋:
id 為 1 的產品僅在 2019 年春季銷售。
id 為 2 的產品在 2019 年春季銷售,但也在 2019 年春季之后銷售。
id 為 3 的產品在 2019 年春季之后銷售。
我們只返回 id 為 1 的產品,因為它是 2019 年春季才銷售的產品。
解析
這題有坑點,不仔細的人是通不過的。首先,題目求的是售出的產品,所以如果產品id不在銷售表中就無需展示,所以需要用內連接而不是左連接。連接完后按產品id分組,由于題目返回的是產品id和名稱,所以Oracle中需要同時對產品id和名稱分組。坑點來了,題目要求的是篩選僅在2019年春季售出的產品,僅在2019春季指一個產品對應的所有日期都在2019春季。不難想到,若該產品對應的售出日期的最小值不小于2019年春季第一天,最大值不超過2019年春季最后一天,則為僅在2019春季售出的產品。
算法(標準SQL)
內連接產品表和銷售表,連接條件為產品表.產品id=銷售表.產品id,再對產品id和名稱分組,再篩選銷售日期都在2019春季的產品,即該產品對應的售出日期的最小值不小于2019-01-01,最大值不大于2019-03-31,最后返回產品id和名字即可。
代碼(標準SQL)
select p.product_id,p.product_name
from Product p
join Sales s
on p.product_id=s.product_id
group by p.product_id,p.product_name
having min(sale_date)>=date'2019-01-01'
and max(sale_date)<=date'2019-03-31';