2011-01-14 79 views
19

有人可以給我看一個示例SQL服務器腳本,我可以看看它使用了「With Clause」使用「With Clause」SQL Server 2008

我想用這個子句遍歷200個數據庫,這些數據庫包含了我試圖運行查詢的同一個表。我試圖避免使用遊標,因爲查詢時間太長以及使用while循環。

有人可以告訴我,我能做些什麼。

謝謝。

+1

`WITH`不會幫你完成這個任務。所有的數據庫都在同一個實例上嗎?你在所有這些代碼上運行的代碼是什麼? – 2011-01-14 21:21:19

+3

引用[公主新娘](http://www.imdb.com/title/tt0093779/)的Inigo Montoya:「你一直用這個詞,我認爲這不代表你的想法。」 :-) – 2011-01-14 21:23:24

+1

馬丁,是的,他們是在同一個實例。每個數據庫都有相同的表格。我想使用sum函數從表中收集所有數據,並將每個數據庫的名稱填充到臨時表中,其中包含以下列:DBNAME,IMG_COUNT,DATE。表的名稱是tbldoc或dbo.tbldoc。每個數據庫都包含這個表格,並且都有我想要查詢的相同列。如何加快速度,而不是使用遊標或while循環? – Jeff 2011-01-14 22:33:34

回答

31

只是一捅,但這裏的另一種方式來寫FizzBu​​zz :) 100行就足以顯示WITH語句,我想。

;WITH t100 AS (
SELECT n=number 
FROM master..spt_values 
WHERE type='P' and number between 1 and 100 
)     
SELECT 
    ISNULL(NULLIF(
    CASE WHEN n % 3 = 0 THEN 'Fizz' Else '' END + 
    CASE WHEN n % 5 = 0 THEN 'Buzz' Else '' END, ''), RIGHT(n,3)) 
FROM t100 

但身後的實際功率(被稱爲公用表表達式http://msdn.microsoft.com/en-us/library/ms190766.aspx「CTE」),在SQL Server 2005及以上的遞歸,下面在表格爲通過反覆增加了虛表的建立每一次。

;WITH t100 AS (
SELECT n=1 
union all 
SELECT n+1 
FROM t100 
WHERE n < 100 
)     
SELECT 
    ISNULL(NULLIF(
    CASE WHEN n % 3 = 0 THEN 'Fizz' Else '' END + 
    CASE WHEN n % 5 = 0 THEN 'Buzz' Else '' END, ''), RIGHT(n,3)) 
FROM t100 

要運行的所有數據庫的類似查詢,您可以使用無證sp_msforeachdb。在另一個答案中已經提到它,但它是sp_msforeachdb,而不是sp_foreachdb。

雖然使用它時要小心,因爲有些東西不是你所期望的。考慮這個例子

exec sp_msforeachdb 'select count(*) from sys.objects' 

而不是每個數據庫中的對象的數量,你會得到報道的相同的計數,開始,目前的DB的。 爲了解決這個問題,請首先「使用」數據庫。請注意方括號以限定多字數據庫名稱。

exec sp_msforeachdb 'use [?]; select count(*) from sys.objects' 

對於您關於填充理貨表的具體查詢,可以使用類似下面的內容。不確定DATE列,所以此Tally表只有DBNAME和IMG_COUNT列,但希望它可以幫助您。

create table #tbl (dbname sysname, img_count int); 

exec sp_msforeachdb ' 
use [?]; 
if object_id(''tbldoc'') is not null 
insert #tbl 
select ''?'', count(*) from tbldoc' 

select * from #tbl 
1

嘗試sp_foreachdb過程。

+0

這只是使用光標,所以可能不會在OP的當前系統上產生戲劇性的速度性能(不是我懷疑這將會成爲可能) – 2011-01-14 21:27:07

7

有兩種類型的WITH子句:

這裏是SQL形式FizzBu​​zz,使用具有共同表表達式(CTE)。

;WITH mil AS (
SELECT TOP 1000000 ROW_NUMBER() OVER (ORDER BY c.column_id) [n] 
FROM master.sys.all_columns as c 
CROSS JOIN master.sys.all_columns as c2 
)     
SELECT CASE WHEN n % 3 = 0 THEN 
      CASE WHEN n % 5 = 0 THEN 'FizzBuzz' ELSE 'Fizz' END 
     WHEN n % 5 = 0 THEN 'Buzz' 
     ELSE CAST(n AS char(6)) 
    END + CHAR(13) 
FROM mil 

這裏是一個SELECT語句也使用WITH子句

SELECT * FROM orders WITH (NOLOCK) where order_id = 123