如何在数据库Oracle中选择薪水第二高的记录?

时间:2013-04-30 06:08:12

标签: sql oracle

假设我有一个具有id,user_name,salary的表员工。如何在Oracle中选择薪水第二高的记录?

我用谷歌搜索,找到这个解决方案,以下是对的吗?:

select sal from
     (select rownum n,a.* from
        ( select distinct sal from emp order by sal desc) a)
where n = 2;

18 个答案:

答案 0 :(得分:21)

RANK和DENSE_RANK已被建议 - 根据您的要求,您可能还会考虑ROW_NUMBER():

select * from (
  select e.*, row_number() over (order by sal desc) rn from emp e
)
where rn = 2;

RANK(),DENSE_RANK()和ROW_NUMBER()之间的区别归结为:

  • ROW_NUMBER()始终生成唯一排名;如果ORDER BY子句无法区分两行,它仍然会给它们不同的排名(随机)
  • RANK()和DENSE_RANK()将对ORDER BY子句无法区分的行赋予相同的排名
  • DENSE_RANK()将始终生成一个连续的等级序列(1,2,3,...),而RANK()将在两个或更多行具有相同等级后留下空白(想想“奥运会”:如果两名运动员获得金牌,没有第二名,只有第三名)

所以,如果你只想要一名员工(即使有几名员工的薪水最高),我建议你推荐ROW_NUMBER()。

答案 1 :(得分:4)

如果您使用的是Oracle 8+,则可以使用RANK()DENSE_RANK()这样的功能

SELECT *
FROM (
  SELECT some_column, 
         rank() over (order by your_sort_column desc) as row_rank
) t
WHERE row_rank = 2;

答案 2 :(得分:3)

此查询适用于 SQL * PLUS ,以查找第二高薪 -

SELECT * FROM EMP
WHERE SAL = (SELECT MAX(SAL) FROM EMP
WHERE SAL < (SELECT MAX(SAL) FROM EMP));

这是双子查询

我希望这可以帮助你......

答案 3 :(得分:2)

WITH records
AS
(
    SELECT  id, user_name, salary,
            DENSE_RANK() OVER (PARTITION BY id ORDER BY salary DESC) rn
    FROM    tableName
)
SELECT  id, user_name, salary
FROM    records 
WHERE   rn = 2

答案 4 :(得分:1)

你应该使用这样的东西:

SELECT *
FROM (select salary2.*, rownum rnum from
         (select * from salary ORDER BY salary_amount DESC) salary2
  where rownum <= 2 )
WHERE rnum >= 2;

答案 5 :(得分:1)

select * from emp where sal=(select max(sal) from emp where sal<(select max(sal) from emp))

所以在我们的emp表中(默认由oracle提供)这里是输出

EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO


  7698 BLAKE      MANAGER         7839 01-MAY-81       3000            30
  7788 SCOTT      ANALYST         7566 19-APR-87       3000            20
  7902 FORD       ANALYST         7566 03-DEC-81       3000            20

或者只是想要显示第二个最高薪水

select max(sal) from emp where sal<(select max(sal) from emp)

MAX(SAL)

  3000

答案 6 :(得分:1)

我建议在Oracle中实现以下两种方法。

  1. 使用子查询:
  2. select distinct SALARY   
    from EMPLOYEE e1  
    where 1=(select count(DISTINCT e2.SALARY) from EMPLOYEE e2 where         
      e2.SALARY>e1.SALARY);
    

    这是获取所需输出的非常简单的查询。但是,这个查询非常慢,因为内部查询中的每个薪水都与所有不同的工资进行比较。

    1. 使用DENSE_RANK():
    2. select distinct SALARY   
      from
        (
          select e1.*, DENSE_RANK () OVER (order by SALARY desc) as RN 
          from EMPLOYEE e
        ) E
       where E.RN=2;
      

      这是非常有效的查询。它适用于DENSE_RANK(),与RANK()不同,它分配连续的等级,根据行号分配下一个等级,就像奥运会一样。

      RANK()和DENSE_RANK()之间的区别: https://oracle-base.com/articles/misc/rank-dense-rank-first-last-analytic-functions

答案 7 :(得分:1)

从员工中选择Max(Salary)作为SecondHighestSalary,其中Salary不在 (从员工中选择max(Salary))

答案 8 :(得分:1)

select * FROM (
select EmployeeID, Salary
, dense_rank() over (order by Salary DESC) ranking
from Employee
)
WHERE ranking = 2;

dense_rank()用于工资必须相同。所以它给出了正确的输出,而不是使用 rank()

答案 9 :(得分:0)

您可以使用两个最大功能。假设从SALARY_TBL获取userid = 10及其第二高薪水的数据。

select max(salary) from SALARY_TBL
where 
userid=10
salary <> (select max(salary) from SALARY_TBL where userid=10)

答案 10 :(得分:0)

SELECT * FROM EMP WHERE SAL =(从EMP WHERE SAL中选择MAX(SAL)<(从EMP中选择MAX(SAL)));

(或) 通过SAL DESC从EMP订单中选择ENAME,SAL;

(或) SELECT * FROM(选择ENAME,SAL,DENSE_RANK() R = 2时从EMP超出(按拼写排序或按SAL DESC排序的顺序)R;

答案 11 :(得分:0)

select max(Salary) from EmployeeTest where Salary < ( select max(Salary) from EmployeeTest ) ;

这适用于所有数据库。

答案 12 :(得分:0)

select * from emp where sal = (
select sal from
     (select rownum n,a.sal from
    ( select distinct sal from emp order by sal desc) a)
where n = 2);

这是更优化的,适合所有场景......

答案 13 :(得分:0)

此查询可以帮助我每次遇到这样的问题。将N替换为位置..

select *
from(
     select *
     from (select * from TABLE_NAME order by SALARY_COLUMN desc)
     where rownum <=N
    )
where SALARY_COLUMN <= all(
                select SALARY_COLUMN
                from (select * from TABLE_NAME order by SALARY_COLUMN desc)
                where rownum <=N
               );

答案 14 :(得分:0)

我相信这将完成相同的结果,没有子查询或排名功能:

SELECT *
FROM emp
ORDER BY sal DESC
LIMIT 1
OFFSET 2

答案 15 :(得分:-1)

为Sql server

语法
SELECT MAX(Salary) as 'Salary' from EmployeeDetails
where Salary NOT IN
(
SELECT TOP n-1 (SALARY) from EmployeeDetails ORDER BY Salary Desc
)

要获得员工的第二高薪,我们需要将“n”替换为2个我们的查询,就像这样

SELECT MAX(Salary) as 'Salary' from EmployeeDetails
where Salary NOT IN
(
SELECT TOP 1 (SALARY) from EmployeeDetails ORDER BY Salary Desc
)

员工的第3高薪

SELECT MAX(Salary) as 'Salary' from EmployeeDetails
where Salary NOT IN
(
SELECT TOP 2 (SALARY) from EmployeeDetails ORDER BY Salary Desc
)

答案 16 :(得分:-1)

用最高数字替换N

SELECT *
FROM Employee Emp1
WHERE (N-1) = (
SELECT COUNT(DISTINCT(Emp2.Salary))
FROM Employee Emp2
WHERE Emp2.Salary > Emp1.Salary)

解释

如果您之前没有看到类似的内容,上面的查询会非常混乱 - 内部查询就是所谓的相关子查询,因为内部查询(子查询)使用外部查询中的值(在这种情况下)它的WHERE子句中的Emp1表。

Source

<强> I have given the answer here

顺便提一句,我将此问题标记为重复。

答案 17 :(得分:-2)

select salary from EmployeeDetails order by salary desc limit 1 offset (n-1).

如果您希望找到第二高于替换n的{​​{1}}。