簡體   English   中英

SQL 查詢根據另一列中的最大值更新記錄

[英]SQL query to update a record based on the max value in another column

問題

我有這張桌子。 (您也可以在DBFiddle中查看它。)

ID 版本 編號。 筆記
1個 NULL 31
2個 1個 31 可口
3個 2個 31 有點好吃
4個 NULL 32
5個 1個 32
6個 2個 32 好吧
7 3個 32 極好
8個 NULL 33 矛盾的
9 1個 33 總的
10 2個 33 嘔吐物

第一列是主鍵。 第二和第三列是整數。 第 4 列是 VARCHAR。

對於版本為 NULL 的每個唯一項目編號,我想查看版本值最高的記錄,將其注釋字段的內容復制過來。

這在視覺上更容易理解; 命令運行后,表格應如下所示:

ID 版本 編號。 筆記
1個 NULL 31 有點好吃
2個 1個 31 可口
3個 2個 31 有點好吃
4個 NULL 32 極好
5個 1個 32
6個 2個 32 好吧
7 3個 32 極好
8個 NULL 33 矛盾的
9 1個 33 總的
10 2個 33 嘔吐物

變動說明

  • 對於第 31 項,“kinda tasty”被復制過來,因為它在版本號最高的記錄中,目標單元格未被占用。
  • 對於第 32 項,“fabulous”出於同樣的原因被復制了過來。
  • “puke”未被復制以替換“ambivalent”,因為目標單元格已被占用。

問題

在 SQL 服務器中實現此目的的查詢是什么?

我知道我需要一種按Item No.將記錄分組的方法,找到版本值最高的那個,取其注釋值,並將其復制到版本為 NULL 的記錄中,但我無法將其轉換為SQL。

嘗試這個:

UPDATE t SET notes = (
   SELECT TOP 1 s.notes 
   FROM t s 
   WHERE s.item_no = t.item_no 
   ORDER BY version DESC
) WHERE version IS NULL AND notes IS NULL

檢查演示

使用可更新的 CTE:

WITH cte AS (
  SELECT *, FIRST_VALUE(Notes) OVER (PARTITION BY ItemNo ORDER BY Version DESC) newNotes 
  FROM tablename
)
UPDATE cte
SET Notes = newNotes
WHERE Version IS NULL AND Notes IS NULL;

請參閱演示

創建一個 CTE 以確定我們需要更新的值,然后使用更新連接語法將其連接到原始表:

with maxVal as
(
    select row_number() over (partition by [Item No.] order by Version desc) rn
        , notes
        , [Item No.]
    from TestTable
    where Version is not null
)
update TestTable
set Notes = maxVal.Notes
from TestTable
left join maxVal
    on TestTable.[Item No.] = maxVal.[Item No.]
    and maxVal.rn = 1
where TestTable.Version is null
    and TestTable.Notes = ''

您可以嘗試這種方法:

-- Preparing a table variable
DECLARE @table1 AS TABLE (
    id  INT IDENTITY(1,1) NOT NULL,
    VersionID INT,
    ItemNo INT,
    Note Varchar(50)
)

insert into 
    @table1 (VersionID,ItemNo,Note)
values 
    (NULL,31,''),
    (1,31,'tasty'),
    (2,31,'kinda tasty'),
    (NULL,32,''),
    (1,32,'meh'),
    (2,32,'alright'),
    (3,32,'fabulous'),
    (NULL,33,'ambivalent'),
    (1,33,'gross'),
    (2,33,'puke');

-- update section 
update up set up.Note = db.Note
from @table1 up
inner join 
(
    select a.ItemNo,a.Note
    from @table1 a
    inner join 
    (
        select itemNo,Max(VersionID) as vs
        from @table1
        where Note <> ''
        group by itemNo
    ) as b on a.ItemNo = b.ItemNo and a.VersionID = b.vs
) as db on db.ItemNo = up.ItemNo and up.Note = ''


-- result
select * from @table1

您可以為每個“ Item No. ”選擇最大值,然后用“ Notes ”為NULL的相應值更新原始表。

UPDATE tab 
SET [Notes] = t2.[Notes]
FROM       tab t1 
INNER JOIN (SELECT *, MAX(Version) OVER(PARTITION BY [Item No.]) AS Max_Version
            FROM tab)  t2
        ON t1.[Item No.] = t2.[Item No.]
       AND t2.[Version]  = t2.[Max_Version]
       AND t1.[Notes] IS NULL

此處查看演示。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM