Den bedste måde at gøre dette på er med analytiske funktioner, RANK() eller DENSE_RANK() ...
SQL> select * from (
2 select empno
3 , sal
4 , rank() over (order by sal desc) as rnk
5 from emp)
6 where rnk <= 5
7 /
EMPNO SAL RNK
---------- ---------- ----------
7839 5000 1
7788 3000 2
7902 3000 2
7566 2975 4
8083 2850 5
7698 2850 5
6 rows selected.
SQL>
DENSE_RANK() komprimerer hullerne, når der er uafgjort:
SQL> select * from (
2 select empno
3 , sal
4 , dense_rank() over (order by sal desc) as rnk
5 from emp)
6 where rnk <= 5
7 /
EMPNO SAL RNK
---------- ---------- ----------
7839 5000 1
7788 3000 2
7902 3000 2
7566 2975 3
8083 2850 4
7698 2850 4
8070 2500 5
7 rows selected.
SQL>
Hvilken adfærd du foretrækker afhænger af dine forretningskrav.
Der er også den analytiske funktion ROW_NUMBER(), som vi kan bruge til at returnere et præcist antal rækker. Vi bør dog undgå at bruge løsninger baseret på rækkenummer, medmindre forretningslogikken er glad for vilkårligt at afkorte resultatsættet i tilfælde af uafgjort. Der er forskel på at spørge efter de fem højeste værdier og de første fem poster sorteret efter høje værdier
Der er også en ikke-analytisk løsning, der bruger ROWNUM pseudo-kolonnen. Dette er klodset, fordi ROWNUM anvendes før ORDER BY-udtrykket, hvilket kan føre til uventede resultater. Der er sjældent nogen grund til at bruge ROWNUM i stedet for ROW_NUMBER() eller en af rangeringsfunktionerne.