-2

I have data in my table as below

date                       ID            value
20210109              12           234
20210131              12        456
20210225             23          4567
20210228             23        567
20210315            56      456
20210326           45      3435
20210328          45       4567
20210327            56      12345

My result should be

date                       ID            value
20210131              12        456
20210228             23        567
20210328          45       4567
20210327            56      12345

There could be more ID values for each month but I need the value for the max date for that (id, maxdate). What is the most efficient way to write this query?

John Cappelletti
  • 71,300
  • 6
  • 42
  • 62
Rohitk
  • 9
  • 1
  • Or this?: [Select info from table where row has max date](https://stackoverflow.com/questions/19432913/select-info-from-table-where-row-has-max-date/43963149) – pwilcox Jun 24 '21 at 22:42

3 Answers3

1

You can use row_number():

select t.*
from (select t.*,
             row_number() over (partition by id, year(date), month(date) order by date desc) as seqnum
      from t
     ) t
where seqnum = 1;
Dale K
  • 21,987
  • 13
  • 41
  • 69
Gordon Linoff
  • 1,198,228
  • 53
  • 572
  • 709
0

Just another option via WITH TIES

Example

Select Top 1 with ties * 
 From  YourTable
 Order By row_number() over (partition by left(date,6),id order by date desc)

Results

date        ID  value
20210131    12  456
20210228    23  567
20210328    45  4567
20210327    56  12345

Note:

If your DATE column is actually a date and not an INT or string use left(date,7) in the partition by

John Cappelletti
  • 71,300
  • 6
  • 42
  • 62
  • 1
    Thanks John! Using "ties" is exactly what I wanted here. date column is type date so using left(date,7) give me exactly what I wanted. Thank you! – Rohitk Jun 24 '21 at 23:07
0

Best way to handle these using windows function and CTE or Derived tables.

Here is one way to do so.

SELECT 
    A.id
    , A.[date]
    , A.[value] 
FROM (
    SELECT
        RANK() OVER ( PARTITION BY  id ORDER BY [date] DESC ) AS rank_
        , id
        , date
        , value
    FROM data_max
) AS A
WHERE A.rank_ = 1

Result

Dale K
  • 21,987
  • 13
  • 41
  • 69
Gudwlk
  • 837
  • 8
  • 10