Relative Ranks
Relative Ranks: rank athletes by score and label the top three with medals, keeping output in the original order.
- n == score.length
- 1 <= n <= 10⁴
- 0 <= score[i] <= 10⁶
- All the values in score are unique.
Intuition
Relative ranks assigns placement labels to athletes by score: the top three receive medal names and the rest receive their numeric position.
The complication is that the output must be in the original athlete order, while ranks are determined by sorted order. Sorting the scores directly loses the association between a score and its athlete.
So the indices must travel with the values:
- Sort the indices by their scores descending, so position k in the sorted result tells you which original athlete finished k + 1.
Walking that sorted list, the first three indices get "Gold Medal", "Silver Medal", and "Bronze Medal", and index k beyond that receives the string of k + 1.
Writing to result[originalIndex] is what restores the original ordering — the answer array is filled out of order and read in order.
The medal strings must be exact, including the space and capitalisation. "Gold" alone is a wrong answer, and it is a frustrating one to debug since the logic is otherwise correct.
Ranks are 1-based while indices are 0-based, so the numeric label is k + 1. Off-by-one here shifts every non-medal athlete.
Sorting descending matters — the highest score is rank 1. Ascending order silently produces reversed rankings.
A max-heap is an alternative: push all index-score pairs and pop n times, assigning ranks in pop order. Same O(n log n), no advantage here.
Scores are guaranteed unique, so no tie-breaking rule is needed.
Sort index-score pairs by score descending, then write each rank back to its original index. Carrying the index through the sort is what lets the answer be assembled in the input's order rather than the sorted one.
Approach
Before reading on: price up what enumerating every case costs here, then ask why only the extreme element matters and the rest need no ordering. Aim for O(n log n) time and O(n) space.
Keep indices with scores
Sorting scores alone loses which athlete owns each score. Sort indices by their score instead, so the association survives.
Sort descending
The highest score is rank 1, so sort in decreasing order. Ascending order silently produces reversed rankings that pass no test.
Assign the three medals
The first three sorted positions receive "Gold Medal", "Silver Medal", "Bronze Medal". The exact strings matter — "Gold" alone is wrong.
Number the rest
Position k beyond the medals gets the string of k + 1, since ranks are 1-based while indices are 0-based.
Write to the original index
Store each label at result[originalIndex]. The array is filled out of order and read in order, which is what restores the athlete sequence.
Cost of the approach
Sorting dominates at O(n log n) time, with O(n) space for the index array and result. Scores are unique, so no tie-breaking is needed.
Solution & live demo
Common pitfalls
Losing the original index
sorted_scores = sorted(score, reverse=True) # then no way back to input positions
pairs = sorted(enumerate(score), key=lambda p: -p[1]) answer[orig_i] = ...
The output must line up with the input array, but ranking requires sorted order. Pairing each score with its index preserves the mapping through the sort.
Off-by-one on the numeric rank
answer[orig_i] = str(rank)
answer[orig_i] = str(rank + 1)
Enumeration is zero-based but ranks start at 1, and the fourth-place athlete must read "4". The medals hide the error for the first three, so it only shows up from position four onward.
Sorting ascending and reversing the medal logic
pairs = sorted(enumerate(score), key=lambda p: p[1]) medals for the LAST three
key=lambda p: -p[1] medals[rank] if rank < 3
Two inversions to reason about instead of none, and the numeric ranks then need len - rank arithmetic. Sorting descending makes rank and position the same thing.
Edge cases
the lone score gets 'Gold Medal' regardless of its value
only as many medal labels are assigned as there are athletes; no bronze if there are only two
the sort is a no-op but pairing with indices still happens the same way
ranking depends only on relative order, not on the numeric gaps between scores