Wat is het verschil tussen de functies rank()
en Dense_rank()
? Hoe vind je het nde salaris in de volgende emptbl
tabel?
DEPTNO EMPNAME SAL
------------------------------
10 rrr 10000.00
11 nnn 20000.00
11 mmm 5000.00
12 kkk 30000.00
10 fff 40000.00
10 ddd 40000.00
10 bbb 50000.00
10 ccc 50000.00
Als in de tabelgegevens nulls
staan, wat gebeurt er dan als ik het nth
salaris wil weten?
Antwoord 1, autoriteit 100%
RANK geeft u de rangorde binnen uw bestelde partitie. Ties krijgen dezelfde rangorde, met de volgende rangschikking(en) overgeslagen. Dus als je 3 items op rang 2 hebt, is de volgende rangschikking rang 5.
DENSE_RANK geeft u opnieuw de rangorde binnen uw geordende partitie, maar de rangschikkingen zijn opeenvolgend. Er worden geen rangen overgeslagen als er rangen zijn met meerdere items.
Wat nulls betreft, dit hangt af van de ORDER BY-clausule. Hier is een eenvoudig testscript waarmee je kunt spelen om te zien wat er gebeurt:
with q as (
select 10 deptno, 'rrr' empname, 10000.00 sal from dual union all
select 11, 'nnn', 20000.00 from dual union all
select 11, 'mmm', 5000.00 from dual union all
select 12, 'kkk', 30000 from dual union all
select 10, 'fff', 40000 from dual union all
select 10, 'ddd', 40000 from dual union all
select 10, 'bbb', 50000 from dual union all
select 10, 'xxx', null from dual union all
select 10, 'ccc', 50000 from dual)
select empname, deptno, sal
, rank() over (partition by deptno order by sal nulls first) r
, dense_rank() over (partition by deptno order by sal nulls first) dr1
, dense_rank() over (partition by deptno order by sal nulls last) dr2
from q;
EMP DEPTNO SAL R DR1 DR2
--- ---------- ---------- ---------- ---------- ----------
xxx 10 1 1 4
rrr 10 10000 2 2 1
fff 10 40000 3 3 2
ddd 10 40000 3 3 2
ccc 10 50000 5 4 3
bbb 10 50000 5 4 3
mmm 11 5000 1 1 1
nnn 11 20000 2 2 2
kkk 12 30000 1 1 1
9 rows selected.
Hier is een linknaar een goede uitleg en enkele voorbeelden.
Antwoord 2, autoriteit 37%
Dit artikel hier legt het mooi uit.In wezen kun je het als volgt bekijken:
CREATE TABLE t AS
SELECT 'a' v FROM dual UNION ALL
SELECT 'a' FROM dual UNION ALL
SELECT 'a' FROM dual UNION ALL
SELECT 'b' FROM dual UNION ALL
SELECT 'c' FROM dual UNION ALL
SELECT 'c' FROM dual UNION ALL
SELECT 'd' FROM dual UNION ALL
SELECT 'e' FROM dual;
SELECT
v,
ROW_NUMBER() OVER (ORDER BY v) row_number,
RANK() OVER (ORDER BY v) rank,
DENSE_RANK() OVER (ORDER BY v) dense_rank
FROM t
ORDER BY v;
Het bovenstaande levert het volgende op:
+---+------------+------+------------+
| V | ROW_NUMBER | RANK | DENSE_RANK |
+---+------------+------+------------+
| a | 1 | 1 | 1 |
| a | 2 | 1 | 1 |
| a | 3 | 1 | 1 |
| b | 4 | 4 | 2 |
| c | 5 | 5 | 3 |
| c | 6 | 5 | 3 |
| d | 7 | 7 | 4 |
| e | 8 | 8 | 5 |
+---+------------+------+------------+
In woorden
row_number()
kent een unieke waarde toe aan elke rijrank()
kent hetzelfde rijnummer toe aan dezelfde waarde, waardoor “gaten” overblijvenDense_rank()
kent hetzelfde rijnummer toe aan dezelfde waarde, zodat er geen “gaten” achterblijven
Antwoord 3, autoriteit 4%
rank(): het wordt gebruikt om een record binnen een groep rijen te rangschikken.
dense_rank(): De DENSE_RANK-functie werkt als de RANK-functie, behalve dat het opeenvolgende rangen toewijst.
Query –
select
ENAME,SAL,RANK() over (order by SAL) RANK
from
EMP;
Uitvoer –
+--------+------+------+
| ENAME | SAL | RANK |
+--------+------+------+
| SMITH | 800 | 1 |
| JAMES | 950 | 2 |
| ADAMS | 1100 | 3 |
| MARTIN | 1250 | 4 |
| WARD | 1250 | 4 |
| TURNER | 1500 | 6 |
+--------+------+------+
Query –
select
ENAME,SAL,dense_rank() over (order by SAL) DEN_RANK
from
EMP;
Uitvoer –
+--------+------+-----------+
| ENAME | SAL | DEN_RANK |
+--------+------+-----------+
| SMITH | 800 | 1 |
| JAMES | 950 | 2 |
| ADAMS | 1100 | 3 |
| MARTIN | 1250 | 4 |
| WARD | 1250 | 4 |
| TURNER | 1500 | 5 |
+--------+------+-----------+
Antwoord 4, autoriteit 3%
SELECT empno,
deptno,
sal,
RANK() OVER (PARTITION BY deptno ORDER BY sal) "rank"
FROM emp;
EMPNO DEPTNO SAL rank
---------- ---------- ---------- ----------
7934 10 1300 1
7782 10 2450 2
7839 10 5000 3
7369 20 800 1
7876 20 1100 2
7566 20 2975 3
7788 20 3000 4
7902 20 3000 4
7900 30 950 1
7654 30 1250 2
7521 30 1250 2
7844 30 1500 4
7499 30 1600 5
7698 30 2850 6
SELECT empno,
deptno,
sal,
DENSE_RANK() OVER (PARTITION BY deptno ORDER BY sal) "rank"
FROM emp;
EMPNO DEPTNO SAL rank
---------- ---------- ---------- ----------
7934 10 1300 1
7782 10 2450 2
7839 10 5000 3
7369 20 800 1
7876 20 1100 2
7566 20 2975 3
7788 20 3000 4
7902 20 3000 4
7900 30 950 1
7654 30 1250 2
7521 30 1250 2
7844 30 1500 3
7499 30 1600 4
7698 30 2850 5
Antwoord 5
select empno
,salary
,row_number() over(order by salary desc) as Serial
,Rank() over(order by salary desc) as rank
,dense_rank() over(order by salary desc) as denseRank
from emp ;
row_number()
-> Gebruikt voor het genereren van serienummer
Dense_rank()
zal een continue rang geven, maar rank()
zal rang overslaan in het geval van botsing van rang.
Antwoord 6
Het enige verschil tussen de functies RANK() en DENSE_RANK() is in gevallen waar er een “gelijkspel” is; d.w.z. in gevallen waarin meerdere waarden in een set dezelfde rangorde hebben. In dergelijke gevallen zal RANK() niet-opeenvolgende “rangen” toewijzen aan de waarden in de set (resulterend in hiaten tussen de gehele rangschikkingswaarden wanneer er een gelijkspel is), terwijl DENSE_RANK() opeenvolgende rangschikkingen toekent aan de waarden in de ingesteld (zodat er geen hiaten zijn tussen de gehele rangschikkingswaarden in het geval van een gelijkspel).
Beschouw bijvoorbeeld de set {25, 25, 50, 75, 75, 100}. Voor een dergelijke set geeft RANK() {1, 1, 3, 4, 4, 6} terug (merk op dat de waarden 2 en 5 worden overgeslagen), terwijl DENSE_RANK() {1,1,2,3, 3,4}.
Antwoord 7
Rank() SQL-functie genereert rangorde van de gegevens binnen een geordende reeks waarden, maar de volgende rangorde na de vorige rangorde is rijnummer van die specifieke rij. Aan de andere kant genereert de Dense_Rank() SQL-functie het volgende nummer in plaats van rijnummer te genereren. Hieronder staat het SQL-voorbeeld dat het concept zal verduidelijken:
Select ROW_NUMBER() over (order by Salary) as RowNum, Salary,
RANK() over (order by Salary) as Rnk,
DENSE_RANK() over (order by Salary) as DenseRnk from (
Select 1000 as Salary union all
Select 1000 as Salary union all
Select 1000 as Salary union all
Select 2000 as Salary union all
Select 3000 as Salary union all
Select 3000 as Salary union all
Select 8000 as Salary union all
Select 9000 as Salary) A
Het genereert de volgende uitvoer:
----------------------------
RowNum Salary Rnk DenseRnk
----------------------------
1 1000 1 1
2 1000 1 1
3 1000 1 1
4 2000 4 2
5 3000 5 3
6 3000 5 3
7 8000 7 4
8 9000 8 5
Antwoord 8
Rang en dichte rang geeft de rang in de gepartitioneerde dataset.
Rank() : Het geeft je geen opeenvolgende gehele getallen.
Dense_rank() : Het geeft je opeenvolgende gehele getallen.
In bovenstaande afbeelding is de rangorde van 10008 zip 2 door de functie density_rank() en 24 door de functie rang() aangezien het het rijnummer beschouwt.
Antwoord 9
Rank(), Dense_rank(), row_number()
Dit zijn allemaal vensterfuncties, wat betekent dat ze in eerste instantie als venster fungeren boven een geordende invoerset. Aan deze vensters is afhankelijk van de behoefte een andere functionaliteit gekoppeld. Hier is de bovenstaande 3:
row_number()
Begin met row_number()
omdat dit de basis vormt van deze gerelateerde vensterfuncties. row_number()
zoals de naam suggereert geeft een uniek nummer aan de reeks rijen waarop het is toegepast. Vergelijkbaar met het geven van een serienummer aan elke rij.
rank()
Een subversie van row_number()
kan worden gezegd als rank()
. Rank() wordt gebruikt om hetzelfde serienummer te geven aan die geordende setrijen die duplicaten zijn, maar het houdt de telling nog steeds als vergelijkbaar met een row_number()
voor al diegenen na duplicaten rank() wat betekent vanaf hieronder bijv. Voor gegevens 2 row_number() =rank(), wat betekent dat beide gewoon verschillen in de vorm van duplicaten.
Data row_number() rank() dense_rank()
1 1 1 1
1 2 1 1
1 3 1 1
2 4 4 2
Eindelijk,
Dense_rank() is een uitgebreide versie van rank() zoals de naam doet vermoeden is het compact omdat, zoals je kunt zien in het bovenstaande voorbeeld rank() = dichte_rank() voor alle data 1, maar alleen dat voor data 2 het verschilt in de vorm dat het de volgorde van rang() van vorige rang() handhaaft, niet de feitelijke gegevens
Antwoord 10
Het enige verschil tussen de functies RANK() en DENSE_RANK() is in gevallen waar er een “gelijkspel” is; d.w.z. in gevallen waarin meerdere waarden in een set dezelfde rangorde hebben. In dergelijke gevallen zal RANK() niet-opeenvolgende “rangen” toewijzen aan de waarden in de set (resulterend in hiaten tussen de gehele rangschikkingswaarden wanneer er een gelijkspel is), terwijl DENSE_RANK() opeenvolgende rangschikkingen toekent aan de waarden in de ingesteld (zodat er geen hiaten zijn tussen de gehele rangschikkingswaarden in het geval van een gelijkspel).
Beschouw bijvoorbeeld de set {30, 30, 50, 75, 75, 100}. Voor een dergelijke set geeft RANK() {1, 1, 3, 4, 4, 6} terug (merk op dat de waarden 2 en 5 worden overgeslagen), terwijl DENSE_RANK() {1,1,2,3, 3,4}.