我有一個SQL查詢,返回一組行:SQLServer的SQL查詢與行計數器
SELECT id, name FROM users where group = 2
我需要還包括有一個遞增的整數值的列,所以第一行需要在計數器列中有1,第二個a 2,第三個a 3等
這裏顯示的查詢僅僅是一個簡化的例子,實際上查詢可以是任意複雜的,有多個連接和嵌套查詢。
我知道這可以通過使用具有自動編號字段的臨時表來實現,但是在查詢本身內部有一種方法嗎?
我有一個SQL查詢,返回一組行:SQLServer的SQL查詢與行計數器
SELECT id, name FROM users where group = 2
我需要還包括有一個遞增的整數值的列,所以第一行需要在計數器列中有1,第二個a 2,第三個a 3等
這裏顯示的查詢僅僅是一個簡化的例子,實際上查詢可以是任意複雜的,有多個連接和嵌套查詢。
我知道這可以通過使用具有自動編號字段的臨時表來實現,但是在查詢本身內部有一種方法嗎?
對於初學者來說,沿着線的東西:
SELECT my_first_column, my_second_column,
ROW_NUMBER() OVER (ORDER BY my_order_column) AS Row_Counter
FROM my_table
然而,需要注意的是ROW_NUMBER() OVER (ORDER BY ...)
結構僅確定的Row_Counter
值是非常重要的,它並不能保證結果的排序。
除非SELECT
本身具有明確的ORDER BY
子句,否則可以按任意順序返回結果,具體取決於SQL Server如何決定優化查詢。 (See this article for more info)
,以保證結果將總是可以在Row_Counter
爲了返回的唯一方法是完全一樣的順序同時適用於SELECT
和ROW_NUMBER()
:
SELECT my_first_column, my_second_column,
ROW_NUMBER() OVER (ORDER BY my_order_column) AS Row_Counter
FROM my_table
ORDER BY my_order_column -- exact copy of the ordering used for Row_Counter
上面的圖案將總是以正確的順序返回結果,並且適用於簡單查詢,但是如何處理ORDER BY
子句中可能有幾十個表達式的「任意複雜」查詢?在這種情況下,我更喜歡這樣的事情,而不是:
SELECT t.*
FROM
(
SELECT my_first_column, my_second_column,
ROW_NUMBER() OVER (ORDER BY ...) AS Row_Counter -- complex ordering
FROM my_table
) AS t
ORDER BY t.Row_Counter
使用嵌套查詢意味着沒有必要複製的複雜ORDER BY
條款,這意味着更少的混亂,更容易維護。外部的ORDER BY t.Row_Counter
也使得查詢的目的更加清晰,可以讓你的開發人員更清楚。
在SQL Server 2005及以上者,可以使用ROW_NUMBER()
功能,這對排序順序,並選擇在其上計數完成(和復位)的組。
繼承人一個不同的方法。 如果您有多個不可連接的數據表,或者由於某種原因,您不希望同時統計所有行,但仍希望它們與同一行數相同,則可以創建一個表爲你工作。
實施例:
create table #test (
rowcounter int identity,
invoicenumber varchar(30)
)
insert into #test(invoicenumber) select [column] from [Table1]
insert into #test(invoicenumber) select [column] from [Table2]
insert into #test(invoicenumber) select [column] from [Table3]
select * from #test
drop table #test
的最簡單的方法是使用一個變量行計數器。但是,它將是兩個實際的SQL命令。一到設定的變量,然後查詢,如下所示:如您加入等我通常使這個存儲過程喜歡
SET @n=0;
SELECT @n:[email protected]+1, a.* FROM tablename a
你的查詢可以是複雜的。你可以對變量有各種樂趣,甚至可以用它來計算字段值。關鍵是:=
爲什麼嵌套查詢?通過對ROW_NUMBER()的快速測試,結果查詢最終按照行計數器值排序。 – andynormancx 2009-01-29 18:21:45
上面的嵌套查詢是不必要的,但偶爾可以將「SELECT t。* FROM(...)作爲t WHERE t.Row_Counter BEWEEN 20和30」作爲頁面數據的有效方式編寫。 – Juliet 2009-01-29 18:47:54
如果要確保結果集始終以Row_Counter順序返回以進行「任意複雜」的查詢,則需要嵌套查詢* *。 (有關詳細信息,請參閱http://blogs.msdn.com/queryoptteam/archive/2006/05/02/588731.aspx。) – LukeH 2009-01-30 04:24:32