摘要:[SQL] WHERE 1=1 做什麼用的?
請注意: 本篇單純化討論WHERE 1 = 1用途 無探討SQL injection 無探討StringBuilder等字串組合效能分析 |
情境:
1. 使用者開啟網頁,欲查詢書籍清單
2.(在畫面上選取篩選條件,如作者、出版社...)
3. 按下查詢
4. 頁面上顯示查詢結果
然後我們可能會開始想像這段SQL字串到底要怎麼組合,判別式應該如何寫﹝假設您也沒有使用LINQ to Entity語法協助查詢﹞
那我們開始串接SQL程式碼囉
string sql = "";
bool andFlag = false; //宣告一個旗標決定要不要串上AND字串
sql += "SELECT * ";
sql += "FROM BOOK ";
if(有任何篩選條件){
sql += "WHERE " ;
if(有篩選作者){
sql += "Author = 'author1' ";
andFlag = true;
}
if(有篩選出版社){
if(andFlag)
sql += " AND ";
sql += "Publisher = 'Longman' ";
}
if(有篩選價格){
if(andFlag)
sql += " AND ";
sql += "Price = 100 ";
}
}
//接著進行查詢
上述可以看到為了判別要不要增加AND字串,我們須加上了一些SQL本體以外的旗標(andFlag)及判別式,在整段的流程當中相當的干擾思緒,如果SQL條件一多可能問題就更加嚴重了。
使用WHERE 1 = 1吧
這個條件必定為真,以邏輯面來講它絲毫不影響結果,第一次看到相當令人費解為何會出現這樣的語法,如果以SQL字串組合的流程來說,它就有功效了。請看上述程式碼修改後的範例
string sql = "";
sql += "SELECT * ";
sql += "FROM BOOK ";
sql += "WHERE 1=1 ";
if(有篩選作者)
sql += "AND Author = 'author1' ";
if(有篩選出版社)
sql += "AND Publisher = 'Longman' ";
if(有篩選價格)
sql += "AND Price = 100 ";
//接著進行查詢
只是加上一個WHERE 1 = 1就可以讓程式碼簡潔許多。因為當WHERE條件超過一個時就必須用上條件連接(AND、OR)字串來連結多重條件,但串接時往往又需要判斷連接字串到底要加在前面還是後面,此條件是不是語法當中的最後一項,避免誤加上了後造成語法錯誤。著實麻煩!
延伸使用
SELECT *
FROM BOOK
WHERE 1=0
假設您在某個情況下不想查出任何東西,那就使用WHERE 1 = 0此條件吧
效能議題
雖然加上WHERE 1 = 1可是讓我們程式碼變得簡潔,那我不確定是否會對效能造成影響,所以簡單測試了一下
DECLARE @i INT
DECLARE @N INT
SET @i = 0
SET @N = 1000
WHILE (@i < @N)
BEGIN
SELECT * FROM BOOK
WHERE 1 = 1 --來測試一下這行到底會有多少影響
SET @i+=1
END
此測試TABLE內共有631筆資料,執行1000次SELECT *的結果
有WHERE 執行時間3:52
無WHERE 執行時間3:51
看起來並無效能上的重大影響
結論
增加WHERE 1 = 1不影響輸出結果,但卻可以在SQL語法組合過程中簡化流程,所以偶爾還是可以在程式碼中見到它的身影,下次就會知道它的存在目的了。
參考