简体   繁体   中英

SQL Server 2012 - updating a column based on row to row comparison

I have a table that contains dates and times. For example columns are Date , ExTime , NewTime , Status . I am ordering them based on a expkey column that makes them show in the right order.

I want to do a row by row comparison and compare the second row column of extime to the first row column NewTime . If extime < Newtime then I want to update status with a "1". And then traverse through the table row by row where second row in the above example becomes the first and a new second is pull and used. Here is a sample of what I have now - but it is not hitting and working all all of the rows for some reason.

UPDATE t
SET t.Status = 1
FROM MyTable t
CROSS APPLY (SELECT TOP 1 NewTime
             FROM MyTable
             WHERE ID = t.ID AND [Date] = t.[Date]
             ORDER BY ExpKey) t1
WHERE t.Extime < t1.NewTime

This is not hitting all the rows like I want it to. I have the where clause comparing fields ID and Date to insure that the rows are attached to the same person. If the ID or Dates are not the same it is not attached to the same person so I would not want to update the status. So basically if the ID of Row 2 = ID of Row 1 and Date of Row 2 = Date of Row 1 I want to compare extime of row 2 and see if it is less than newtime of Row 1 - if so then update the status field of row 2.

Any help in figuring out why this sort of works but not on all would be appreciated.

Ad.

On SQL Server 2012 you can easily update status with window function lag() :

with cte as (
    select
        extime,
        lag(newtime) over(partition by id, date order by expKey) as newtime,
        status
    from table1
)
update cte set status = 1 where extime < newtime;

sql fiddle demo

I haven't tested this, but I've dealt with similar issues of comparing adjacent rows. I put this together off-the-cuff, so it may need tweaking, but give it a try.

;WITH CTE AS
(   SELECT ID,[Date],ExpKey,ExTime,NewTime,
    ROW_NUMBER()OVER(PARTITION BY ID,[Date] ORDER BY ExpKey) AS Sort
    FROM MyTable
)
UPDATE row2
SET row2.[Status] = 2
WHERE row2.ExTime < row1.NewTime
FROM CTE row2
CROSS JOIN CTE row1
    ON row1.ID = row2.ID
    AND row1.[Date] = row2.[Date]
    AND row1.Sort = row2.Sort-1 --Join to prior row

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM