2016-03-02 96 views
1

我目前正在处理一个查询,该查询应该返回一个按照邻近给定点排序的CartoDB表(即新表)的子集。我想,通过使用PostgreSQL的ROW_NUMBER()方法,在新的一列显示对应到最近在地图上的标签,第二最接近等,想捕捉:PostgreSQL“列不存在”错误CartoDB

SELECT 
    *, 
    ST_Distance(
     ST_GeomFromText('Point(-73.95623080000001 40.6738101)', 4326)::geography, 
     the_geom::geography 
    )/1609 AS dist, 
    row_number() OVER (ORDER BY dist) as rownum 
FROM locations 
WHERE ST_Intersects(
    ST_GeomFromText(
     'Point(-73.95623080000001 40.6738101)', 4326 
    ), 
    the_geom 
) 
ORDER BY dist ASC 

然而,当我尝试这一点, CartoDB/PostgreSQL返回以下错误:

Error: column "dist" does not exist 

任何关于更好的方法或我失踪的建议?

回答

2

CANT使用在同一级别上计算的字段。

SELECT (x1-x2)^2 + (y1-x2)^2 as dist, dist * 1.6 as miles 
             ^^^^^ 
            undefined 

所以你创建一个子查询。

SELECT dist * 1.6 as miles 
FROM (SELECT (x1-x2)^2 + (y1-x2)^2 as dist 
     FROM table 
    ) T 
+0

有趣的 - 如果主查询是长期和复杂的,有没有更好的“设计”的策略比一切步入一个子查询?具体来说,如果有其他数据被查询(如上例中的*),那么如何在子查询之外访问? – romeboards

+0

我只是简化问题来解决问题。但是,是的,你必须用'*'创建一个子查询,并且计算出的字段 –

+0

即使是'非计算字段'也不能这样使用。 – user2864740

1

您不能在另一列中使用列别名。在这里,您将定义dist作为结果列表,并将其用于row_numberORDER BY。您必须编写与order相同的表达式。

1
SELECT *, 
    row_number() OVER (ORDER BY dist) as rownum 
FROM(
SELECT 
    *, 
    ST_Distance(
     ST_GeomFromText('Point(-73.95623080000001 40.6738101)', 4326)::geography, 
     the_geom::geography 
    )/1609 AS dist 
FROM locations 
WHERE ST_Intersects(
    ST_GeomFromText(
     'Point(-73.95623080000001 40.6738101)', 4326 
    ), 
    the_geom 
) 
) i 
ORDER BY dist ASC 

您不能从同一个访问的别名选择所以把它放在一个内部查询

1

内虽然可以使用派生内部查询(这可能是更容易阅读和可能根据其他RA规则进行优化),也可以使用序号来指代列,因为限制仅适用于新引入的名称

例如,以下是有效的:

SELECT 
    ST_Distance(
     ST_GeomFromText('Point(-73.95623080000001 40.6738101)', 4326)::geography, 
     the_geom::geography 
    )/1609 AS dist 
    -- column ordering changed to make ordinal obvious, as * can bite 
    -- now column 'dist' is the first column and can be referenced by ordinal 
    , row_number() OVER (ORDER BY 1) as rownum 
    , * 
FROM locations 
WHERE ST_Intersects(
    ST_GeomFromText(
     'Point(-73.95623080000001 40.6738101)', 4326 
    ), 
    the_geom 
) 
-- this could also be written as ORDER BY 1 ASC, per ordinal 
ORDER BY dist ASC 
+0

有趣!这种方法似乎比使用子查询更安全。 – romeboards

+0

@romeboards我会说'不那么干扰'。 *但是,它也会导致'沉默破坏';想象有人会改变列的位置,并没有注意到序号的用法 - 现在查询可能仍然是有效的语法,但会产生错误的结果。这是之后移动'*'的一个原因,以避免列隐式滑入。无论如何,这是一种可用的方法。 – user2864740

相关问题