对于连接表中所有缺失的组合,返回 0

itt*_*tus 2 sql postgresql datetime group-by left-join

我有 2 个表、时间序列订单

时间序列

+------------+
|  datetime  |
+------------+
| 2018-11-01 |
| 2018-11-02 |
| 2018-11-03 |
+------------+
Run Code Online (Sandbox Code Playgroud)

订单

+------------+-------------+----------+
|  datetime  | customer_id | order_id |
+------------+-------------+----------+
| 2018-11-01 |           1 |        1 |
| 2018-11-02 |           1 |        2 |
| 2018-11-03 |           2 |        3 |
+------------+-------------+----------+
Run Code Online (Sandbox Code Playgroud)

我想每天获得每个客户的订单数量。

预期成绩:

+------------+-------------+--------------+
|  datetime  | customer_id | number_order |
+------------+-------------+--------------+
| 2018-11-01 |           1 |            1 |
| 2018-11-02 |           1 |            1 |
| 2018-11-03 |           1 |            0 |
| 2018-11-01 |           2 |            0 |
| 2018-11-02 |           2 |            0 |
| 2018-11-03 |           2 |            1 |
+------------+-------------+--------------+
Run Code Online (Sandbox Code Playgroud)

我尝试了 LEFT JOIN,但它不会返回所有客户的所有时间序列

SELECT datetime, customer_id, COUNT(order_id) as number_order 
FROM timeseries
LEFT JOIN orders
ON timeseries.datetime = orders.datetime
GROUP BY datetime, customer_id
ORDER BY datetime, customer_id

>> Result

+------------+-------------+--------------+
|  datetime  | customer_id | number_order |
+------------+-------------+--------------+
| 2018-11-01 |           1 |            1 |
| 2018-11-02 |           1 |            1 |
| 2018-11-03 |           2 |            1 |
+------------+-------------+--------------+
Run Code Online (Sandbox Code Playgroud)

我知道左连接只确保返回 table 中的所有行timeseries,但我需要的是 tabletimeseries中每个 customer_id 的所有行。

感谢您的帮助!

Sal*_*n A 5

您需要交叉连接所有日期和所有客户以获取日期和客户 ID 的所有可能组合。然后左加入订单:

SELECT timeseries.datetime, customers.customer_id, COUNT(orders.order_id) as number_order
FROM timeseries
CROSS JOIN (SELECT DISTINCT customer_id FROM orders) AS customers
LEFT JOIN orders ON orders.datetime = timeseries.datetime AND orders.customer_id = customers.customer_id
GROUP BY timeseries.datetime, customers.customer_id
ORDER BY timeseries.datetime, customers.customer_id
Run Code Online (Sandbox Code Playgroud)