2016-12-02 44 views
2

我有一个数据集,看起来像这样:相对ROW_NUMBER()在PostgreSQL的

SessionID URL    created rownum 
abc www.google.com/page1 2016-08-01 1 
abc www.google.com/page2 2016-08-02 2 
abc www.google.com/blah  2016-08-03 3 
abc www.google.com/page3 2016-08-04 4 
abc www.google.com/page4 2016-08-05 5 

,我想有一个输出看起来像这样:

SessionID URL    created rownum newrownum 
abc www.google.com/page1 2016-08-01 1 -2 
abc www.google.com/page2 2016-08-02 2 -1 
abc www.google.com/blah  2016-08-03 3 0 
abc www.google.com/page3 2016-08-04 4 1 
abc www.google.com/page4 2016-08-05 5 2 

换句话说,我希望看到session正在访问特定页面blah,我希望看到在此特定页面之前和之后访问的页面。请注意,session中的页面按照created字段进行排序。

select 
    sessionid, 
    url, 
    created, 
    row_number() over(partition by sessionid order by created) as rownum 
from 
    <tablename> 
order by 
    sessionid, 
    created 

我不知道如何获取相对于某一页负值行号:

我使用下面的查询产生的rownum列。这是必需的,所以我可以绘制页面blah前后访问的页面种类。当然,可以在同一个会话中对同一页面blah进行多次访问。在这种情况下,应将第一次访问视为第零次访问(newrownum列中的值为0)。

回答

3

这里的东西是一个方法:

select sessionid, url, created, rownum, 
     (rownum - min(case when url = 'blah' then rownum end) over (partition by sessionid) as newrownum 
from (select sessionid, url, created, 
      row_number() over (partition by sessionid order by created) as rownum 
     from <tablename> 
    ) t 
order by sessionid, created; 

换句话说,这个计算的行数'blah'使用另一个窗口函数。在最新版本的Postgres中,您可以使用filter关键字而不是case语句作为条件最小值。

注意:由于min()的原因,这与第一次出现'blah'时的偏差。最后一次使用max()。而且,你的实际逻辑可能会使用类似url like '%blah'之类的东西或者完整的路径名。

+0

非常感谢您提供了一个简单的答案,它非常有意义。工作就像一个魅力:)。 – Patthebug

2

您可以从每个会话的已经计算出的rownum列中减去blah的rownum。

select t.*, rownum-max(case when url like '%blah%' then rownum end) over(partition by sessionid) newrownum 
from (
select 
    sessionid, 
    url, 
    created, 
    row_number() over(partition by sessionid order by created) as rownum 
from 
    <tablename> 
) t 
order by rownum 

获取包含blah使用正则表达式的URL的确切模式匹配,就像url ~ '.+/blah$'

1

根据要用作基准的页码的行号(行0)应用偏移量。在这种情况下,您可以创建一个新的字段作为rownum - 3以实现您正在查找的值。