2017-03-08 43 views
0

比方說,我有表更新選擇與JOIN一個一對多的SQL服務器關係

一個

Col1 Col2 
1 AB 
2 CD 

Col1 Col2 
1 EF 
1 GH 
2 IJ 
2 KL 

如果我有以下查詢

UPDATE A 
SET Col2 = B.Col2 
FROM A 
INNER JOIN B ON A.Col1 = B.Col1 

我試過這個,結果是

一個

Col1 Col2 
1 EF 
2 IJ 

因此,它總是從第一行更新嗎?只是想確保正確的行爲,因爲我即將更新的內容非常關鍵。

+1

號重要的是要知道有天然的「第一行」。您必須始終指定一個「ORDER BY」來指定第一行。它從一個隨機行更新。 (在這種情況下,在許多情況下,您認爲這是一行)要確定用作更新源的內容,您需要從識別並過濾「第一行」的來源進行更新。如果你基於'沒有訂單'的'第一行'的想法構建業務邏輯,你將會有錯誤。 –

回答

1

當您在RDBMS中討論表格時,沒有「第一行」或「最後一行」這樣的定義。如果您沒有指定任何訂單,則數據庫引擎可以將任何記錄用作第一條記錄。當然也有例外,如聚集索引的存在,排序規則等。

如果您沒有指定任何命令,則不能簡單地假定第一條記錄是什麼。

我建議你修改你的查詢,使用你想要更新的值的預定義順序。例如。如果你想更新到一個值第一次來按照字母順序,然後使用該查詢:

UPDATE A 
SET Col2 = B.Col2 
FROM A 
INNER JOIN 
(
SELECT Col1, Col2, 
ROW_NUMBER() OVER(PARTITION BY Col1 ORDER BY Col2) rn 
) 
B ON A.Col1 = B.Col1 AND b.rn=1 

請注意,當您指定訂單的訂貨可以通過完全不同的列設置。想象一下,你有一個DateUpdated列,您希望使用基於最新DateUpdated事件的最新值:

UPDATE A 
SET Col2 = B.Col2 
FROM A 
INNER JOIN 
(
SELECT Col1, Col2, DateUpdated, 
ROW_NUMBER() OVER(PARTITION BY Col1 ORDER BY DateUpdated DESC) rn 
) 
B ON A.Col1 = B.Col1 AND b.rn=1