postgres列别名问题

时间:2009-10-29 18:15:59

标签: sql mysql postgresql alias heroku

作为Postgresql的新手(我正在移动因为我将我的网站移动到只支持它的heroku,我不得不重构我的一些查询和代码。这是一个我不能完全解决的问题通过以下方式了解问题:

PGError: ERROR:  column "l_user_id" does not exist
LINE 1: ...t_id where l.user_id = 8 order by l2.geopoint_id, l_user_id ...
                                                             ^

...查询:

   select distinct 
          l2.*, 
          l.user_id as l_user_id, 
          l.geopoint_id as l_geopoint_id 
     from locations l 
left join locations l2 on l.geopoint_id = l2.geopoint_id 
    where l.user_id = 8 
 order by l2.geopoint_id, l_user_id = l2.user_id desc
添加了

子句“l.user_id as l_user_id,l.geopoint_id as l_geopoint_id”,因为显然postgres不喜欢没有选择字段的order子句。但是我现在得到的错误使它看起来像我也没有得到别名。任何有postgres经验的人都会看到问题吗?

我可能会遇到很多问题 - 查询在mySql中运行良好......

4 个答案:

答案 0 :(得分:15)

在PostgreSQL中,您不能按顺序使用带别名的表达式。只有普通的别名在那里工作。您的查询应如下所示:

   select distinct 
          l2.*, 
          l.user_id as l_user_id, 
          l.geopoint_id as l_geopoint_id 
     from locations l 
left join locations l2 on l.geopoint_id = l2.geopoint_id 
    where l.user_id = 8 
 order by l2.geopoint_id, l.user_id = l2.user_id desc;

我认为你的意思是l2.user_id=l.user_id应该先行。

PostgreSQL通用邮件列表上的

This is relevant message。以下内容属于documentation of ORDER BY clause

  

每个表达式可以是名称或   输出的序号   列 (SELECT列表项)或它   可以是一个形成的任意表达式   来自输入列

使用表达式时没有别名。

答案 1 :(得分:4)

你有:

order by l2.geopoint_id, l_user_id = l2.user_id desc
在您的查询中

。那是非法的语法。删除= l2.user_id部分(如果这是其中一个连接条件,则将其移至where)并且它应该可以正常工作。

更新以下选择(删除了= l2.user_id)应该可以正常工作。我在Postgres 8.3

上测试了它(显然有不同的表/列名称)
select distinct 
       l2.*, 
       l.user_id as l_user_id, 
       l.geopoint_id as l_geopoint_id 
  from locations l 
  left join locations l2 on l.geopoint_id = l2.geopoint_id 
 where l.user_id = 8 
 order by l2.geopoint_id, l_user_id desc

答案 2 :(得分:4)

我使用fuzzystrmatch中的函数遇到了同样的问题 - 尤其是levenshtein函数。我需要按字符串距离排序,并按字符串距离过滤结果。我最初在尝试:

SELECT thing.*, 
levenshtein(thing.name, '%s') AS dist 
FROM thing 
WHERE dist < character_length(thing.name)/2 
ORDER BY dist

但是,当然,我从WHERE子句得到错误“column”dist“不存在”。我试过这个并且有效:

SELECT thing.*, 
(levenshtein(thing.name, '%s')) AS dist 
FROM thing 
ORDER BY dist

但是我需要在WHERE子句中拥有该限定条件。此问题中的其他人说在WHDER子句之前评估WHERE子句,因此在评估WHERE子句时该列不存在。按照这个建议,我发现嵌套的SELECT语句可以解决这个问题:

SELECT * FROM 
(SELECT thing.*, 
     (levenshtein(thing.name, '%s')) AS dist 
     FROM thing 
     ORDER BY dist
) items 
WHERE dist < (character_length(items.name)/2)

请注意,“items”表别名是必需的,dist列别名可在外部SELECT中访问,因为它在语句中是唯一的。它有点时髦,我很惊讶它必须在PG中这样 - 但它似乎没有受到性能影响所以我很满意。

答案 3 :(得分:1)

“之所以被添加,是因为显然postgres不喜欢没有选择字段的订单子句”

“就顺序而言 - 是的,PostgresQL(以及许多其他数据库)不允许按SELECT子句中未列出的列进行排序。”

简直不真实。

=&GT; SELECT id FROM t1 ORDER BY owner LIMIT 5;

id

30  10  20  50  40 (5行)