程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 數據庫知識 >> SqlServer數據庫 >> 關於SqlServer >> 執行一次SQL查詢,UPDATE多行記錄

執行一次SQL查詢,UPDATE多行記錄

編輯:關於SqlServer
 

通常情況下,我們會使用以下SQL語句來更新字段值:

1
  UPDATE mytable SET myfield='value' WHERE other_field='other_value';

     但是,如果你想更新多行數據,並且每行記錄的各字段值都是各不一樣,你會怎麼辦呢?舉個例子,我的博客有三個分類目錄(免費資源、教程指南、櫥窗展示),這些分類目錄的信息存儲在數據庫表categories中,並且設置了顯示順序字段 display_order,每個分類占一行記錄。如果我想重新編排這些分類目錄的順序,例如改成(教程指南、櫥窗展示、免費資源),這時就需要更新categories表相應行的display_order字段,這就涉及到更新多行記錄的問題了,剛開始你可能會想到使用循環執行多條UPDATE語句的方式,就像以下的php程序示例:

1
2
3
4
  foreach ($display_order as $id => $ordinal) {
    $sql="UPDATE categories SET display_order = $ordinal WHERE id = $id";
    mysql_query($sql);
}

     這種方法並沒有什麼任何錯誤,並且代碼簡單易懂,但是在循環語句中執行了不止一次SQL查詢,在做系統優化的時候,我們總是想盡可能的減少數據庫查詢的次數,以減少資源占用,同時可以提高系統速度。幸運的是,還有更好的解決方案,只不過SQL語句稍微復雜點,但是只需執行一次查詢即可,語法如下:

1
2
3
4
5
6
7
  UPDATE mytable
    SET myfield = CASE other_field
        WHEN 1 THEN 'value'
        WHEN 2 THEN 'value'
        WHEN 3 THEN 'value'
    END
WHERE id IN (1,2,3)

     回到我們剛才的分類目錄的例子,我們可以使用以下SQL語句:

1
2
3
4
5
6
7
  UPDATE categories
    SET display_order = CASE id
        WHEN 1 THEN 3
        WHEN 2 THEN 1
        WHEN 3 THEN 2
    END
WHERE id IN (1,2,3)

     這樣的SQL語句是很容易理解的,也就是用到了很多編程語言都有的關鍵字 CASE,根據id字段值來進行不同分支的當型判斷,進而更新display_order字段值。例如原來id=1的記錄的display_order改成了3,id=2的記錄的display_order改成了1,只需執行一次查詢即可更新多行記錄。在通常情況,WHERE子句是可有可無的,添加該WHERE子句的意義與其他用到WHERE子句的普通SQL是一樣的。如果你使用的MySQL數據庫,可以進一步閱讀MySQL關於CASE語句的文檔說明:CASE Statement

     如果你需要更新一行記錄的多個字段,可以用以下SQL語句:

1
2
3
4
5
6
7
8
9
10
11
12
  UPDATE categories
    SET display_order = CASE id
        WHEN 1 THEN 3
        WHEN 2 THEN 4
        WHEN 3 THEN 5
    END,
    title = CASE id
        WHEN 1 THEN 'New Title 1'
        WHEN 2 THEN 'New Title 2'
        WHEN 3 THEN 'New Title 3'
    END
WHERE id IN (1,2,3)

     以上方案大大減少了數據庫的查詢操作次數,大大節約了系統資源,但是該怎樣與我們的編程語言結合起來呢?我們還是用剛才分類目錄的例子,以下是php的程序示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
  $display_order = array(
    1 => 4,
    2 => 1,
    3 => 2,
    4 => 3,
    5 => 9,
    6 => 5,
    7 => 8,
    8 => 9
);

$ids = implode(',', array_keys($display_order));
$sql = "UPDATE categories SET display_order = CASE id ";
foreach ($display_order as $id => $ordinal) {
    $sql .= sprintf("WHEN %d THEN %d ", $id, $ordinal);  // 拼接SQL語句
}
$sql .= "END WHERE id IN ($ids)";
echo $sql;
mysql_query($sql);

     在這個例子中總共更新了8行數據,但是只執行了一次數據庫查詢,相比於循環執行8次UPDATE語句,以上例子所節約的時間可以說是微不足道的。但是想想,當你需要更新10,0000或者更多行記錄時,你會發現這其中的好處!唯一要注意的問題是SQL語句的長度,需要考慮程序運行環境所支持的字符串長度,我目前獲得的數據:SQL語句長度達到1,000,960在php中仍然可以順利執行,我查詢了php文檔並沒有發現明確規定字符串最大長度。

 
  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved