【问题标题】:Postgresql WHERE with age() function [duplicate]带有age()函数的Postgresql WHERE [重复]
【发布时间】:2018-09-30 09:27:08
【问题描述】:

我很确定以前有人问过这个问题,但我正在努力为包含类似数据的表获取正确的语法

id  date        type                                    report  item_id
1   2018-11-07  Veröffentlichung des 9-Monats-Berichtes TRUE    16
2   2018-11-06  Veröffentlichung des 9-Monats-Berichtes TRUE    17
3   2019-03-07  Veröffentlichung des Jahresberichtes    TRUE    17
4   2019-05-10  Bericht zum 1. Quartal                  TRUE    17

我试图制定的查询是

SELECT date, AGE(now(), date) as t1
FROM dates
WHERE t1 > 0

意思是我只寻找过去的价值。
但是,我得到一个错误

错误:“t1”列不存在

(当然是别名)。 Postgresql 这里不支持别名吗?

【问题讨论】:

  • t1(间隔)与0(数字)不可比

标签: sql postgresql alias


【解决方案1】:

您不能在WHERE 条件中引用别名,因为逻辑上WHERESELECT 之前执行。

你可以使用子查询:

SELECT * 
FROM (SELECT date, AGE(now(), date) as t1
      FROM dates) sub
WHERE sub.t1 > interval '0::seconds';

或者LATERAL(我最喜欢的方式):

SELECT date, s.t1
FROM dates
,LATERAL (SELECT AGE(now(), date) as t1) AS s
WHERE s.t1 > interval '0::seconds';

或者重复表达(违反DRY principle):

SELECT date, AGE(now(), date) as t1
FROM dates
WHERE AGE(now(), date) > interval '0::seconds';

至于计算AGE你并不需要它,因为你可以将它重写为date > now()


相关文章:

PostgreSQL: using a calculated column in the same query

MySQL - Search into a custom Column

Why do “linq to sql” queries starts with the FROM keyword unlike regular SQL queries?

【讨论】:

  • 不要使用子查询。 CTE 是优化栅栏,在这里没有帮助。
  • 你能详细说明一下LATERAL吗?而且我确实一直在努力成为DRY
  • 现在我得到HINT: No operator matches the given name and argument type(s). You might need to add explicit type casts.
  • @Jan Sure,更新了我的答案
  • @LukaszSzozda:谢谢!
【解决方案2】:

如果您赶时间并且有一个(有序的)日期索引,请不要这样做。

因为此查询可以使用索引,只需在编码工作上进行少量投资即可获得巨大的性能提升。

SELECT date, AGE(now(), date) AS t1
FROM dates
WHERE date > now();

我说now(),因为你这样做了,但也许你想要CURRENT_DATE 代替

要创建一个合适的索引做

create index dates_date on dates(date);

【讨论】:

  • 感谢您的回答 - 我如何将表格更改为有索引?
猜你喜欢
  • 2013-05-01
  • 2013-09-26
  • 2018-11-12
  • 2018-05-26
  • 2017-11-18
  • 2023-03-14
  • 2018-06-25
  • 2019-06-14
  • 2011-01-23
相关资源
最近更新 更多