当按照与ID无关的条件排序时,选择出现在具有给定ID的行之后的行

时间:2013-04-19 12:54:13

标签: sql postgresql activerecord

鉴于“人”表中的数据:

+----+-------+
| id | name  |
+----+-------+
|  1 | Jane  |
|  2 | Joe   |
|  4 | John  |
|  5 | Alice |
|  6 | Bob   |
+----+-------+

顺序:

SELECT * FROM people ORDER BY name

......将返回:

+----+-------+
| id | name  |
+----+-------+
|  5 | Alice |
|  6 | Bob   |
|  1 | Jane  |
|  2 | Joe   |
|  4 | John  |
+----+-------+

如何编写一个查询 - 包括上面的顺序 - 只返回具有给定id的行之后的行,例如,如果给定id为1,它将返回:

+----+-------+
| id | name  |
+----+-------+
|  2 | Joe   |
|  4 | John  |
+----+-------+

要清楚,id是可变的,并且事先不知道。

使用普遍支持的SQL的方法会很棒,但如果它们有任何其他用途,我会使用PostgreSQL 9.2和ActiveRecord 3.2,例如OVER()和ROW_NUMBER()。

[编辑]我之前显示了错误的所需结果集,包括具有给定id的行。但是,如问题中所述,结果集应仅包含给定ID之后的行

2 个答案:

答案 0 :(得分:6)

select *
from people
where
    name >= (
        select name
        from people
        where id = 1
    )
    and id != 1
order by name

答案 1 :(得分:1)

到目前为止,我发现了一种最简单的方法,用于需要精度的情况,例如,在具有不同ID值的多个调用中没有丢失或重复的结果是组合窗口函数和CTE,如:

WITH ordered_people AS (
  SELECT *, ROW_NUMBER() OVER (ORDER BY name) AS n
  FROM people
  ORDER BY name
)

SELECT * 
  FROM ordered_people
  WHERE n > (SELECT n FROM ordered_people WHERE id = 1)
  ORDER BY name
;