2016-01-21 31 views
1

我在使用Google BigQuery中的LAST_VALUE()窗口函数时遇到问题。带有ASC的LAST_VALUE()和带有DESC的FIRST_VALUE返回不同的结果

在我的理解中,以下两列应该返回相同的结果,但实际上它们会返回不同的结果,并且似乎FIRST_VALUE()的结果是正确的。

SELECT 
    FIRST_VALUE(status) OVER (PARTITION BY userId ORDER BY timestamp DESC), 
    LAST_VALUE(status) OVER (PARTITION BY userId ORDER BY timestamp ASC) 
FROM 
    [table] 

我犯了什么错误吗?

+0

没有空或重复。更糟的是,使用LAST_VALUE的那个会为同一个userId返回不同的结果。 – yuzwyy

+0

这是一个功能,而不是bug ..检查下面的答案 –

+0

你有一个低利率。重要的是,您必须使用投票下方发布答案左侧的勾号标记接受的答案。这会增加你的速度。看看这个工程通过visinting这个链接:http://meta.stackoverflow.com/questions/5234/how-does-accepting-an-answer-work#5235 – Pentium10

回答

0

OVER()函数在具有(ORDER BY)时如何工作有一个微妙之处:它们以递增方式工作。 BY你得到增量结果与订单 - 这是你在你的结果见证了什么:

看到这个查询:

SELECT x, y, 
     FIRST_VALUE(x) OVER(ORDER BY y) first, 
     LAST_VALUE(x) OVER(ORDER BY y DESC) last, 
     SUM(x) OVER() plain_sum_over, 
     SUM(x) OVER(ORDER BY y) sum_over_order 
FROM (SELECT 1 x, 1 y),(SELECT 2 x, 2 y),(SELECT 3 x, 3 y),(SELECT 4 x, 4 y) 

enter image description here

plain_sum_oversum_over_order泄露秘密。

+0

谢谢! 我明白SUM()增量工作,但LAST_VALUE()也增量工作? 如果我想获得每个用户的最后状态,最好的方法是什么? – yuzwyy

+1

好的。我想现在我明白了这种行为。因此,如果在没有窗口框架子句的OVER子句中有ORDER BY,则默认窗口框架为RANGE BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW。它是否正确? – yuzwyy

+0

Correcto!就是这样 –

相关问题