top n queries using the offset clause - sql

SELECT last_name
FROM employees
order by last_name DESC
fetch first 5 rows only;
I am a beginner in SQL. I am trying to run this query but keep getting an error
sql command not properly ended
What am I doing wrong?

oracle version < 12
select * from
(select last_name, row_number() over(order by last_name desc nulls last) rnm
from employees)
where rnm<=5;
oracle version 12
SELECT last_name
FROM employees
ORDER BY last_name DESC
OFFSET 1 ROWS FETCH NEXT 5 ROWS ONLY;

Related

fetch the 1st row from the table for an employee with highest salary [duplicate]

This question already has answers here:
How do I limit the number of rows returned by an Oracle query after ordering?
(14 answers)
Closed 3 years ago.
I am searching for a query to find the details of highest paid employee in the entire organization. I am using oracle DB.
Queries which I tried are:
select * from EMP order by SAL desc FETCH FIRST 1ROW ONLY;
ERROR: SQL command not properly ended
select * from EMP order by SAL desc where rownum = 1;
ERROR: SQL command not properly ended
select * from EMP order by SAL desc LIMIT 0 , 1;
ERROR: SQL command not properly ended
You could use:
SELECT *
FROM (SELECT * FROM emp ORDER BY sal DESC)
WHERE ROWNUM = 1
Please note that if rows have identifical salaries, ROWNUMBER will rank them randomly. To handle ties, you could use RANK() instead (or maybe DENSE_RANK(), depending on your needs):
SELECT *
FROM (
SELECT
e.*,
RANK() OVER(ORDER BY sal DESC) rn
FROM emp
)
WHERE rn = 1
There is an issue with all three statements.
Try this:
select * from EMP order by SAL desc FETCH FIRST ROW ONLY;
or use an analytical function ROW_NUMBER:
SELECT T.* FROM
(SELECT
T.*, ROW_NUMBER() OVER(ORDER BY SAL DESC NULLS LAST) RN
FROM EMP) T
WHERE RN = 1
Cheers!!

Oracle SQL Finding the 5 lowest salaries

I am trying to answer the following question. Show ID_Number and name for the five lowest paid employees.
This is the table with employees:
CREATE TABLE Employees
(ID_No CHAR(4) NOT NULL,
Name VARCHAR(50) NOT NULL,
Hire_Date DATE NOT NULL,
Position VARCHAR(20) CHECK(Position IN('CHAIRMAN','MANAGER','ANALYST','DESIGNER','PROGRAMMER','SALES REP','ADMIN','ACCOUNTANT')),
Salary NUMERIC(8,2) NOT NULL,
Mgr_ID_No CHAR(4) NULL,
Dept_No SMALLINT NULL);
I will add that I've been trying a few methods and "limit" and "top" do not work for some reason.
In Oracle 12c :
-- more than 5 rows being returned, if multiple rows
-- match the value of the 5th row
SELECT e.ID_No, e.Name
FROM Employees e
ORDER BY e.Salary
FETCH FIRST 5 ROWS WITH TIES;
-- only 5 rows being returned, even if multiple rows
-- match the value of the 5th row
SELECT e.ID_No, e.Name
FROM Employees e
ORDER BY e.Salary
FETCH FIRST 5 ROWS ONLY;
-- NEXT clause may be replaced with FIRST
SELECT e.ID_No, e.Name
FROM Employees e
ORDER BY e.Salary
FETCH NEXT 5 ROWS ONLY;
Prior to Oracle 12c :
SELECT e.ID_No, e.Name
FROM ( SELECT ID_No, Name, row_number() over (order by salary) seq FROM Employees ) e
WHERE e.seq <= 5
ORDER BY e.seq;
queries may be used for Top-N Queries
SELECT ID_NO, NAME
FROM EMPLOYEES
ORDER BY SALARY
FETCH FIRST 5 ROWS ONLY
The row_number() window function should work here (note that window functions can't be used in WHERE/HAVING clauses).
SELECT ID_No, Name
FROM (SELECT ID_No, Name, Row_Number() OVER (ORDER BY Salary) RN
FROM Employees)
WHERE RN <= 5;
In Oracle ROWNUM could be used.
SELECT *
FROM (SELECT ID_No,
Name
FROM Employees
ORDER BY Salary) x
WHERE ROWNUM <= 5;
Another method could be a subquery counting the rows with lower or equal salary.
SELECT EO.ID_No,
EO.Name
FROM Employees EO
WHERE (SELECT COUNT(*)
FROM Emplyoees EI
WHERE EI.Salary <= EO.Salary) <= 5;

LIMIT does not work with UNION [duplicate]

This question already has answers here:
How do I limit the number of rows returned by an Oracle query after ordering?
(14 answers)
Closed 5 years ago.
What is wrong with below code?
SELECT first_name, last_name
FROM employees
UNION ALL
SELECT first_name, last_name
FROM dependents
ORDER BY last_name
LIMIT 6 OFFSET 1;
Even a simple query with LIMIT doesn't seem to be working :
SELECT first_name, last_name
FROM dependents
ORDER BY last_name
LIMIT 6 OFFSET 1;
Getting this error repeatedly: ORA-00933: SQL command not properly
ended
I believe oracle does not support LIMIT. Try this
ORDER BY last_name
OFFSET 1 ROWS FETCH NEXT 6 ROWS ONLY;
Note this syntax supports from Oracle 12c
What is wrong with the code is that Oracle does not support limit. Period. The most recent versions support the ANSI standard fetch first <n> rows only.
Perhaps you intend:
SELECT e.*
FROM (SELECT e.*, ROW_NUMBER() OVER (ORDER BY last_name) as seqnum
FROM (SELECT first_name, last_name FROM employees
UNION ALL
SELECT first_name, last_name
FROM dependents
) e
ORDER BY last_name
) e
WHERE seqnum BETWEEN 1 and 7;

ORACLE 12C - SELECT query using ROWNUM

I have to get second five (6-10) best salaries records from sorted table using ROWNUM.
Using ROWNUM is necessary.
When I execute query:
SELECT ROWNUM AS position, name, salary
FROM (SELECT name, salary
FROM employees
ORDER BY salary DESC)
WHERE ROWNUM <= 10;
I get a first 10 best records.
And now when I try execute query:
SELECT ROWNUM AS position, name, salary
FROM (SELECT name, salary
FROM employees
ORDER BY salary DESC)
WHERE ROWNUM >= 6 AND ROWNUM <= 10;
I get a empty table. Why doesn't it work?
As explained in the documentation, rownum is evaluated as the rows are fetched. If you never fetch the first row, you never get to the second. Hence, no rows are fetched:
Conditions testing for ROWNUM values greater than a positive integer
are always false. For example, this query returns no rows:
SELECT * FROM employees
WHERE ROWNUM > 1;
But, more importantly, you are using Oracle 12C. So, use fetch first instead of rownum. This has multiple advantages. Besides being standard SQL, you don't need a subquery:
SELECT name, salary
FROM employees
ORDER BY salary DESC
FETCH FIRST 10 ROWS ONLY;
And for your second:
SELECT name, salary
FROM employees
ORDER BY salary DESC
OFFSET 5 ROWS
FETCH FIRST 5 ROWS ONLY;
I write in queston that using ROWNUM is necessary, because it's
academic task.
In such a case use a subquery
SELECT name, salary
FROM (
SELECT name, salary, ROWNUM as my_rownum
FROM employees
ORDER BY salary DESC
)
WHERE my_rownum BETWEEN 6 AND 10
You can use below query and try....
SELECT name,salary from
( SELECT name,salary, DENSE_RANK() OVER (ORDER BY salary DESC) as rn
from employees )
where rn between 6 and 10;

sql query to fetch top 3 salaries

emp_name |salary
---------------
A |12568
B |3000
C |7852
D |2568
E |9852
F |1598
G |8569
I want a sql query to fetch the lowest 3 salaried employees
If you are using Oracle 12c or later you can make your query simpler with fetch. Instead of writing inner queries like this.
SELECT *
FROM
(SELECT * FROM EMPLOYEES EMP ORDER BY EMP.SALARY ASC
)
WHERE ROWNNUM <= 3
You can combine them into a single query.
SELECT * FROM employees emp ORDER BY emp.salary ASC
FETCH FIRST 3 ROWS ONLY;
More Information on the syntax and construct is available here.
http://www.dba-oracle.com/t_offset_fet_first_rows_only.htm
ORACLE:
SELECT emp_name
FROM ( SELECT *
FROM employees e
ORDER BY e.salary ASC)
WHERE ROWNUM < 4
Good luck!
You can use top 3 to get three record after ordering them in descending or ascending order. I have SQL server syntax but you can have idea from this for you target DBMS.
For top three max salaries
Select top 3 emp_name, salary
order by salary desc
For top three minimum salaries
Select top 3 emp_name, salary
order by salary asc
USE ASC AND LIMIT
Select emp_name, salary FROM TABLE_NAME
order by salary ASC LIMIT 3;
You didn't specify your DBMS, so this is ANSI SQL:
select emp_name, salary
from (
select emp_name, salary,
dense_rank() over (order by salary) as rnk
from employees
) t
where rnk <= 3;
This will also deal with employees that have the same salary. So the result might be more then three rows if more then one of the employees with the lowest salary have the same salary.