我有以下SQL查询:
SELECT (SELECT ...) AS X, (SELECT ...) AS Y from my_table
'X' 非常难计算,它被用作计算 Y 的输入。然而,如果我试图在计算 Y 的查询内部或甚至主查询内部引用 X,就会出现以下错误消息:
Error: column "X" does not exist
在计算X后是否有任何方法可以引用它?我真的不想重复计算它,因为这似乎非常低效。
我有以下SQL查询:
SELECT (SELECT ...) AS X, (SELECT ...) AS Y from my_table
'X' 非常难计算,它被用作计算 Y 的输入。然而,如果我试图在计算 Y 的查询内部或甚至主查询内部引用 X,就会出现以下错误消息:
Error: column "X" does not exist
在计算X后是否有任何方法可以引用它?我真的不想重复计算它,因为这似乎非常低效。
PostgreSQL通常很聪明,不需要计算两次相同的内容。因此,像这样的查询:
SELECT (SELECT hard_to_compute FROM whatever) AS X,
(SELECT hard_to_compute FROM whatever)*2 AS Y
FROM my_table
应该只需要运行两个子查询一次。但是如果查询像这样
SELECT (SELECT hard_to_compute FROM whatever) AS X,
(SELECT hard_to_compute*2 FROM whatever) AS Y
FROM my_table
那么,优化器可能更难看出这两个查询中相同的部分。
另一种处理方法是创建一个稳定函数来计算X。只要输入相同,在单个语句内,稳定函数总是返回相同的结果,因此Postgres知道它只需要运行一次。请参见http://www.postgresql.org/docs/9.0/interactive/xfunc-volatility.html。
您可以使用子查询来实现,例如:
select *, hard_to_compute * 2 as using_hard_to_compute \
from (select *, (i * i) as hard_to_compute from foo) bar;
i | hard_to_compute | using_hard_to_compute
---+-----------------+-----------------------
1 | 1 | 2
2 | 4 | 8
3 | 9 | 18
当然,i * i
并不难计算。在这个例子中,我只是假装它很难。
(SELECT ...) AS X
部分,将其结果存储在一个临时表中。然后在主查询中使用该临时表。