Oracle
 sql >> Cơ Sở Dữ Liệu >  >> RDS >> Oracle

Các hàm RANK, DENSE_RANK và ROW_NUMBER trong Oracle

Các hàm Oracle Analytic tính toán một giá trị tổng hợp dựa trên một nhóm các hàng được gọi là cửa sổ, xác định phạm vi các hàng được sử dụng để thực hiện các phép tính cho hàng hiện tại. Sau đây là các hàm Phân tích được sử dụng nhiều nhất.
- RANK, DENSE_RANK và ROW_NUMBER
- LAG và LEAD
- FIRST_VALUE và LAST_VALUE

Tôi sẽ thảo luận về các hàm phân tích RANK, DENSE_RANK và ROW_NUMBER. Chúng khá giống nhau về bản chất và chúng ta cần sử dụng trên cơ sở yêu cầu. Tôi cũng sẽ giải thích sự khác biệt giữa chúng

Đây là cú pháp chung

 analytic_osystem ([đối số]) HẾT ([query_partition_clause] [order_by_clause]) 

ROW_NUMBER hàm trong Oracle

ROW_NUMBER chỉ định một số duy nhất cho mỗi hàng của cùng một cửa sổ trong chuỗi các hàng có thứ tự được chỉ định bởi order_by_clause.

Trước tiên hãy tạo dữ liệu mẫu

 TẠO BẢNG "DEPT" ("DEPTNO" NUMBER (2,0), "DNAME" VARCHAR2 (14), "LOC" VARCHAR2 (13), CONSTRAINT "PK_DEPT" PRIMARY KEY ("DEPTNO")) TẠO BẢNG " EMP "(" EMPNO "NUMBER (4,0)," ENAME "VARCHAR2 (10)," JOB "VARCHAR2 (9)," MGR "NUMBER (4,0)," HIREDATE "DATE," SAL "NUMBER (7 , 2), SỐ "COMM" (7,2), SỐ "DEPTNO" (2,0), CONSTRAINT "PK_EMP" PRIMARY KEY ("EMPNO"), CONSTRAINT "FK_DEPTNO" FOREIGN KEY ("DEPTNO") TÀI LIỆU THAM KHẢO "DEPT "(" DEPTNO ") BẬT); SQL> desc empName Null? Nhập ---- ---- ----- EMPNO NOT NULL NUMBER (4) ENAME VARCHAR2 (10) JOB VARCHAR2 (9) MGR NUMBER (4) HIREDATE DATESAL NUMBER (7,2) COMM NUMBER (7,2 ) SỐ DEPTNO (2) SQL> desc deptName Null? Nhập ---- ----- ---- DEPTNO NOT NULL NUMBER (2) DNAME VARCHAR2 (14) LOC VARCHAR2 (13) chèn vào các giá trị DEPT (10, 'ACCOUNTING', 'NEW YORK'); chèn vào giá trị ghi nợ (20, 'NGHIÊN CỨU', 'DALLAS'); chèn vào giá trị ghi nợ (30, 'NGHIÊN CỨU', 'DELHI'); chèn vào giá trị dept (40, 'NGHIÊN CỨU', 'MUMBAI'); cam kết; chèn vào giá trị emp (7839, 'Clark', 'MANAGER', 7839, to_date ('9-6-2008', 'dd-mm-yyyy'), 28573, null, 10); chèn vào giá trị emp (7782, 'Clara ',' MANAGER ', 7839, to_date (' 9-6-2008 ',' dd-mm-yyyy '), 0, null, 10); chèn vào các giá trị emp (7934,' Blake ',' MANAGER ', 7839 , to_date ('1-5-2007', 'dd-mm-yyyy'), 0, null, 10); chèn vào giá trị emp (7788, 'Scott', 'ANALYST', 7788, to_date ('9-6 -2012 ',' dd-mm-yyyy '), 30000, null, 20); chèn vào các giá trị emp (7902,' Bill ',' ANALYST ', 7832, to_date (' 9-6-2012 ',' dd- mm-yyyy '), 30000, null, 20); chèn vào các giá trị emp (7876,' TPM ',' ANALYST ', 7566, to_date (' 9-6-2017 ',' dd-mm-yyyy '), 11000 , null, 20); chèn vào các giá trị emp (7369, 'TPM1', 'ANALYST', 7566, to_date ('9-6-2017', ' dd-mm-yyyy '), 8000, null, 20); chèn vào các giá trị emp (7698,' A1 ',' ANALYST ', 7788, to_date (' 9-6-2017 ',' dd-mm-yyyy ') , 28500, null, 30); chèn vào các giá trị emp (7499, 'A2', 'ANALYST', 7698, to_date ('9-7-2017', 'dd-mm-yyyy'), 16000, null, 30); chèn vào các giá trị emp (7844, 'A3', 'ANALYST', 7698, to_date ('9-7-2017', 'dd-mm-yyyy'), 15000, null, 30); chèn vào giá trị emp (7654 , 'A4', 'ANALYST', 7698, to_date ('9-7-2017', 'dd-mm-yyyy'), 12500, null, 30); chèn vào các giá trị emp (7521, 'A5', 'ANALYST ', 7698, to_date (' 9-7-2017 ',' dd-mm-yyyy '), 12500, null, 30); chèn vào các giá trị emp (7900,' A6 ',' ANALYST ', 77698, to_date (' 9-7-2017 ',' dd-mm-yyyy '), 0, null, 30); cam kết; 
 SQL> desc emp Tên Null? Gõ phím ----------------------------------------- -------- ---------------------------- SỐ EM KHÔNG ĐẦY ĐỦ (4) ENAME VARCHAR2 (10) CÔNG VIỆC VARCHAR2 (9) SỐ MGR (4) SỐ BÁN HÀNG NGÀY HIREDATE (7,2) SỐ COMM (7,2) SỐ DEPTNO (2) SQL> select deptno, count (*) from emp group by deptno; DEPTNO COUNT (*) ---------- ---------- 30 6 20 4 10 3SQL> selectdeptno, ename, sal, row_number () over (phân vùng theo thứ tự deptno theo sal) "row_number" fromemp; DEPTNO ENAME SAL row_number ---------- ---------- ------------- 10 CLARK 0 1 10 MILLER 0 210 allen 28573 320 SMITH 8000 120 ADAMS 11000 220 SCOTT 30000 320 FORD 30000 430 JAMES 9500 130 MARTIN 12500 230 WARD 12500 330 TURNER 15000 430 ALLEN 16000 530 BLAKE 28500 6 13 hàng được chọn. 

Hàm RANK trong Oracle

RANK gần giống như ROW_NUMBER nhưng các hàng có giá trị bằng nhau, trong cùng một cửa sổ, mà thứ tự theo mệnh đề được chỉ định sẽ nhận cùng một thứ hạng nhưng hàng tiếp theo nhận RANK như ROW_NUMBER.

 SQL> selectdeptno, ename, sal, rank () over (phân vùng theo thứ tự deptno theo sal) "RANK" fromemp; DEPTNO ENAME SAL RANK ---------------- - ---------- ---------- 10 CLARK 0 1 10 MILLER 0 210 allen 28573 320 SMITH 8000 120 ADAMS 11000 220 SCOTT 30000 320 FORD 30000 330 JAMES 9500 130 MARTIN 12500 230 WARD 12500 230 TURNER 15000 430 ALLEN 16000 530 BLAKE 28500 6 13 hàng được chọn. 

Hàm Dense_rank trong Oracle

DENSE_RANK gần giống như RANK, nhưng nó không để lại khoảng cách giữa các hàng nếu một hoặc nhiều giá trị giống nhau. Giống như trong ví dụ sau TURNER bên cạnh WARD trong cùng một nhóm nhận được DENSE_RANK 3.

 SQL> selectdeptno, ename, sal, secure_rank () over (phân vùng theo thứ tự deptno theo sal) "DENSE_RANK" fromemp; DEPTNO ENAME SAL DENSE_RANK ---------------- - ---------- ---------- 10 CLARK 0 1 10 MILLER 0 210 allen 28573 320 SMITH 8000 120 ADAMS 11000 220 SCOTT 30000 320 FORD 30000 330 JAMES 9500 130 MARTIN 12500 230 WARD 12500 230 TURNER 15000 330 ALLEN 16000 430 BLAKE 28500 5 Đã chọn 13 hàng. 

Chúng tôi cũng có thể đặt cả ba trong một truy vấn duy nhất

 select deptno, ename, sal, row_number () over (phân vùng theo thứ tự deptno theo sal) "row_number", rank () over (phân vùng theo thứ tự deptno theo sal) "rank", secure_rank () over (phân vùng theo deptno đặt hàng bởi sal) "dày đặc_rank" từ emp; DEPTNO ENAME SAL hàng_số xếp hạng dày đặc ----------------- ---------------- ------ ---------- 10 CLARK 0 1 1 1 10 MILLER 0 2 1 1 10 allen 28573 3 3 2 20 SMITH 8000 1 1 1 20 ADAMS 11000 2 2 2 20 SCOTT 30000 3 3 3 20 FORD 30000 4 3 3 30 JAMES 9500 1 1 1 30 MARTIN 12500 2 2 2 30 WARD 12500 3 2 2 30 TURNER 15000 4 4 3 30 ALLEN 16000 5 5 4 30 BLAKE 28500 6 6 513 hàng được chọn.  

Chúng ta có thể sử dụng Row_number và hàm RANK để xóa các hàng trùng lặp

 delete from t where rowid IN (select rid from (select rowid rid, row_number () over (phân vùng theo thứ tự tên cột theo rowid) rn from t) where rn <> 1); 

Hàm này rất hữu ích cho các truy vấn top-N và bottom-N.

SQL dưới đây có thể được sử dụng để tìm mức lương cao nhất trong mỗi khoản nợ

 SQL> select * (selectdeptno, ename, sal, row_number () over (phân vùng theo thứ tự deptno theo sal) "row_number" fromemp) trong đó row_number =1; 

Hy vọng bạn thích giải thích về RANK, DENSE_RANK và ROW_NUMBER như các hàm Oracle Analytic và cách chúng tôi có thể sử dụng trong truy vấn để phân tích dữ liệu. Chúng tôi phải rất cẩn thận khi sử dụng các hàm này trong các truy vấn nếu không kết quả sẽ khác.

Các bài viết có liên quan

Hàm LEAD trong Oracle
Các hàm phân tích trong oracle
Câu hỏi phỏng vấn Oracle
Oracle Set Operators
Hướng dẫn Oracle Sql
Tài liệu về oracle xếp hạng dày đặc


  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Khai báo ngoại lệ do người dùng xác định bằng phương pháp RAISE_APPLICATION_ERROR trong cơ sở dữ liệu Oracle

  2. Bảo mật cơ sở dữ liệu Oracle - Mã hóa và giải mã

  3. chia chuỗi thành nhiều hàng

  4. Chuyển đổi múi giờ trong truy vấn SQL

  5. Hàm LTRIM () trong Oracle