我有两个Postgres表(实际上,不止于此,但为了问题而简化) - 一个是客户订购的产品记录,另一个是每个客户的价格历史记录和日期生效了。像这样:
customer_id | timestamp | quantity
------------+---------------------+---------
1 | 2015-09-29 16:01:01 | 5
1 | 2015-10-23 14:33:36 | 3
2 | 2015-10-19 09:43:02 | 7
1 | 2015-11-16 15:08:32 | 2
customer_id | effective_time | price
------------+---------------------+-------
1 | 2015-01-01 00:00:00 | 15.00
1 | 2015-10-01 00:00:00 | 12.00
2 | 2015-01-01 00:00:00 | 14.00
我正在尝试创建一个查询,该订单将在订单时返回该客户的每个订单及其单价,如下所示:
customer_id | quantity | price
------------+----------+------
1 | 5 | 15.00
1 | 3 | 12.00
2 | 7 | 14.00
1 | 2 | 12.00
这基本上就是我想要的,但我知道你不能在内部查询中引用外部查询,而且我无法弄清楚如何重新考虑因素:
SELECT
o.customer_id,
o.quantity,
p.price
FROM orders o
INNER JOIN (
SELECT price
FROM prices x
WHERE x.customer_id = o.customer_id
AND x.effective_time <= o.timestamp
ORDER BY x.effective_time DESC
LIMIT 1
) p
;
有人能建议最好的方法吗?
答案 0 :(得分:1)
您可以在SELECT列表中执行子查询,而不是基于prices
表加入内联视图:
SELECT customer_id, quantity, (
SELECT price
FROM prices p
WHERE
p.customer_id = o.customer_id
AND p.effective_time <= o.timestamp
ORDER BY p.effective_time DESC
LIMIT 1
) AS price
FROM orders o
这确实依赖于相关的子查询,这可能对性能有害,但是对于数据结构的方式,我怀疑是否有更好的选择。
答案 1 :(得分:1)
你不需要子查询,只需要一个简单的内部联接(这假设每个客户没有重复的effective_times):
SELECT o.customer_id, o.quantity
,p.price
FROM orders o
JOIN prices p ON p.customer_id = o.customer_id
AND p.effective_time <= o.timestamp
AND NOT EXISTS ( SELECT * FROM prices nx
WHERE nx.customer_id = o.customer_id
AND nx.effective_time <= o.timestamp
AND nx.effective_time > p.effective_time
)
;