2012-02-16 61 views
20

我试图通过包裹在我头上的功能来获得结束和分区。这是一个我只是不明白的例子。试图了解over()和分区

这里是我拥有的数据:

SALESORDERID  ORDERDATE 
43894    08/01/2001 
43664    07/01/2001 
43911    08/01/2001 
43867    08/01/2001 
43877    08/01/2001 
44285    10/01/2001 
44501    11/01/2001 
43866    08/01/2001 
43895    08/01/2001 
43860    08/01/2001 

当我运行此查询:

select Row_Number() over(partition by orderdate order by orderdate asc) 
    as Rownumber, salesorderid, orderdate 
from test2 
order by rownumber 

下面是结果我得到:

ROWNUMBER  SALESORDERID  ORDERDATE 
1    43664    07/01/2001 
1    43911    08/01/2001 
1    44109    09/01/2001 
1    44483    11/01/2001 
1    44285    10/01/2001 
2    43867    08/01/2001 
2    44501    11/01/2001 
3    43895    08/01/2001 
4    43894    08/01/2001 
5    43877    08/01/2001 

有人能解释一下这个查询对我来说。我对SQL不是陌生的,但是我一直在努力寻找窗口,并且无法让我的头部缠绕在这里。

回答

26

尝试排序,你会看到的结果更容易

select Row_Number() over(partition by orderdate order by orderdate asc) 
    as Rownumber, salesorderid, orderdate 
from test2 
order by orderdate; 

应该给(我已经添加了清晰的空行)

ROWNUMBER  SALESORDERID  ORDERDATE 
1    43664    07/01/2001 

1    43911    08/01/2001 
2    43867    08/01/2001 
3    43895    08/01/2001 
4    43894    08/01/2001 
5    43877    08/01/2001 

1    44109    09/01/2001 

1    44285    10/01/2001 

1    44483    11/01/2001 
2    44501    11/01/2001 

你会发现,结果被分成'分区',每个分区是具有相同命令的一组行。这就是“按订单分区”的意思。

在一个分区内,行按orderdate排序,按照'(by order order order by orderdate asc)分区的第二个子句''。这不是非常有用,因为分区内的所有行将具有相同的orderdate。因此,分区内的行的排序是随机的。尝试按照partition by子句中的salesorderid进行排序,以获得更加可重现的结果。

ROW_NUMBER()只是返回每个分区

+1

也可以尝试SELECT COUNT(*)OVER(分区....)中的行的顺序可能是更清楚你它在做什么。 – 2012-02-16 16:42:32

+0

谢谢你的回答。分区子句非常强大 – Luke101 2012-02-17 16:13:07

+0

非常感谢! – 2014-08-27 17:50:48

9

partition by orderdate表示您只是将记录与具有相同orderdate的其他记录进行比较。例如,在orderdate = '08/01/2001'的五条记录中,一条将具有row_number() = 1,一条将具有row_number() = 2,依此类推。

order by orderdate asc意味着在一个分区内,行号将按照orderdate的顺序分配。在你的例子中没有任何效果,因为你已经分区了orderdate,所以分区中的所有记录将具有相同的orderdate。 (这就像写作SELECT ... FROM t WHERE c = 6 ORDER BY c:所有选定的记录具有相同的值c,因此ORDER BY c什么都不做)。因此,在一个分区内,row_number()的赋值是任意的:每行都有不同的数字,但是没有保证哪一行有哪个号码。通过订单日期

+0

这个答案应该被接受,而不是 – Avi 2016-12-11 22:28:51