Reputation: 2313
I'm looking to get the largest value in a set of columns, as well as the column name. For example, given:
| Id | A | B | C |
------------------
| 1 | 1 | 2 | 3 |
I would expect:
| Id | Column | Value |
------------------------
| 1 | C | 3 |
I've already gotten the part of the query to determine the greatest value, but I'm struggling to display what column it came from as well.
SELECT Id,
(SELECT Max(v)
FROM (VALUES (A), (B), (C)) AS value(v)) as MaxValue
FROM [dbo].[MyTable]
I feel like I'm really close, but I'm not sure how to finish this off. Thanks!
Upvotes: 2
Views: 80
Reputation: 5231
One way (not claiming it's the best way) to attack your problem is to rank your column values, and then select what we want from that data set.
First to unpivot your record(s):
select id
, columnName
, columnValue
from mytable
unpivot
(
columnValue for columnName in(a,b,c)
) as unpvt
Next, we can assign a ranking to the values based on what we want to see output. To rank the largest column value for an ID 1st, we add:
select id
, columnName
, columnValue
, rank() over (partition by id order by columnValue DESC, columnName DESC) as rankVal
from mytable
unpivot
(
columnValue for columnName in(a,b,c)
) as unpvt
Note that above in our rank()
, if we order just by columnValue
, you would end up with two rank 1s if two columns had the same max value. The next step would then return two records for an ID
. If this is the output you would want to see, remove the , columnName DESC
from the rank()
order by.
Now that we have our values ranked, we can select what we want from that result set:
with cteUnpivot(id, columnName, columnValue, rankVal)
AS
(
select id
, columnName
, columnValue
, rank() over (partition by id order by columnValue DESC, columnName DESC) as rankVal
from mytable
unpivot
(
columnValue for columnName in(a,b,c)
) as unpvt
)
select id
, columnName as [Column]
, columnValue as [Value]
from cteUnpivot
where rankVal = 1
Upvotes: 2