【问题标题】:What is the simplest SQL Query to find the second largest value?查找第二大值的最简单的 SQL 查询是什么?
【发布时间】:2010-09-07 02:55:18
【问题描述】:

在特定列中查找第二大整数值的最简单 SQL 查询是什么?

列中可能存在重复值。

【问题讨论】:

  • 为此目的使用偏移量...从 [dbo] 中选择扩展名。[Employees] 按扩展名排序 desc 偏移量 2 行仅获取接下来的 1 行

标签: sql puzzle


【解决方案1】:

最简单的方法是在应用程序中从此结果集中获取第二个值:

SELECT DISTINCT value 
FROM Table 
ORDER BY value DESC 
LIMIT 2

但是如果你必须使用 SQL 选择第二个值,如何:

SELECT MIN(value) 
FROM ( SELECT DISTINCT value 
       FROM Table 
       ORDER BY value DESC 
       LIMIT 2
     ) AS t

【讨论】:

  • 你在 SQL Server 上运行过这个吗?
  • @Craig - LIMIT 是 MySql 语法,问题没有指定 SQL 版本。
【解决方案2】:

我想你可以这样做:

SELECT * 
FROM Table 
ORDER BY NumericalColumn DESC 
LIMIT 1 OFFSET 1

SELECT * 
FROM Table ORDER BY NumericalColumn DESC 
LIMIT (1, 1)

取决于您的数据库服务器。提示:SQL Server 不做 LIMIT。

【讨论】:

  • update-SQL Server 2012 添加了类似于上述dbadiaries.com/…的offset / fetch 子句
  • 假设您有 2 个元素具有相同的值但也是最大的元素。我想你必须这样做OFFSET 2
  • 添加 GROUP BY 子句将满足其中的重复条件。
【解决方案3】:
SELECT MAX( col )
  FROM table
 WHERE col < ( SELECT MAX( col )
                 FROM table )

【讨论】:

  • Matt 和 Vinoy 的回答也会处理重复项。假设重复最大值,然后使用马特的答案将产生正确的第二大值,而如果您使用 top 2 descmin 方法,您可能会得到最大值.
  • 如果有多个第二高怎么办...那么这不会给出所有元组
  • 谢谢,用这个找到倒数第二个日期here
  • 比我在内部语句中使用 ORDER_BY 和 LIMIT 的方法要好得多
  • 请注意,如果在请求的记录之前没有记录,这将不会返回结果。
【解决方案4】:
select top 1 MyIntColumn from MyTable
where
 MyIntColumn <> (select top 1 MyIntColumn from MyTable order by MyIntColumn desc)
order by MyIntColumn desc

【讨论】:

    【解决方案5】:

    这适用于 MS SQL:

    select max([COLUMN_NAME]) from [TABLE_NAME] where [COLUMN_NAME] < 
     ( select max([COLUMN_NAME]) from [TABLE_NAME] )
    

    【讨论】:

      【解决方案6】:

      这样的?不过,我还没有测试过:

      select top 1 x
      from (
        select top 2 distinct x 
        from y 
        order by x desc
      ) z
      order by x
      

      【讨论】:

        【解决方案7】:

        在T-Sql中有两种方式:

        --filter out the max
        select max( col )
        from [table]
        where col < ( 
            select max( col )
            from [table] )
        
        --sort top two then bottom one
        select top 1 col 
        from (
            select top 2 col 
            from [table]
            order by col) topTwo
        order by col desc 
        

        在 Microsoft SQL 中,第一种方式的速度是第二种方式的两倍,即使有问题的列是集群的。

        这是因为与max 聚合使用的表或索引扫描相比,排序操作相对较慢。

        或者,在 Microsoft SQL 2005 及更高版本中,您可以使用 ROW_NUMBER() 函数:

        select col
        from (
            select ROW_NUMBER() over (order by col asc) as 'rowNum', col
            from [table] ) withRowNum 
        where rowNum = 2
        

        【讨论】:

          【解决方案8】:

          How to select the nth row in a SQL database table?

          Sybase SQL Anywhere 支持:

          SELECT TOP 1 START AT 2 value from table ORDER BY value
          

          【讨论】:

            【解决方案9】:

            我在这里看到了一些特定于 SQL Server 的解决方案和一些特定于 MySQL 的解决方案,因此您可能需要澄清您需要哪个数据库。虽然如果我不得不猜测我会说 SQL Server,因为这在 MySQL 中是微不足道的。

            我还看到了一些不起作用的解决方案,因为它们没有考虑到重复的可能性,因此请注意您接受哪些解决方案。最后,我看到一些可行的方法,但会对表进行两次完整扫描。您要确保第二次扫描只查看 2 个值。

            SQL Server(2012 年之前):

            SELECT MIN([column]) AS [column]
            FROM (
                SELECT TOP 2 [column] 
                FROM [Table] 
                GROUP BY [column] 
                ORDER BY [column] DESC
            ) a
            

            MySQL:

            SELECT `column` 
            FROM `table` 
            GROUP BY `column` 
            ORDER BY `column` DESC 
            LIMIT 1,1
            

            更新:

            SQL Server 2012 现在支持更简洁的(和standard)OFFSET/FETCH 语法:

            SELECT [column] 
            FROM [Table] 
            GROUP BY [column] 
            ORDER BY [column] DESC
            OFFSET 1 ROWS
            FETCH NEXT 1 ROWS ONLY;
            

            【讨论】:

            • 这是我希望看到的。如果您需要它为任何n 工作,接受的答案就会变得丑陋。这个经得起考验。
            • @RobinMaben Robin,最大值重复的场景怎么样?假设一列包含数字 1 到 100,但 100 重复了两次。那么这个解决方案将产生第二大的值 100,这是不正确的。对吗?
            • @PankajSharma 不,这仍然有效,因为 GROUP BY 子句
            • 这是执行此操作的标准方法。接受的答案应该更新为这个。
            • 我收到一条错误消息,提示我不能在同一查询中使用 TOPOFFSET
            【解决方案10】:
            select * from emp e where 3>=(select count(distinct salary)
                from emp where s.salary<=salary)
            

            此查询选择最多三个薪水。如果两个 emp 获得相同的薪水,这不会影响查询。

            【讨论】:

              【解决方案11】:

              使用相关查询:

              Select * from x x1 where 1 = (select count(*) from x where x1.a < a)
              

              【讨论】:

                【解决方案12】:

                Tom,当select max([COLUMN_NAME]) from [TABLE_NAME] 部分返回多个值时,相信这将失败。即数据集中有两个以上的值。

                对您的查询稍作修改即可 -

                select max([COLUMN_NAME]) 
                from [TABLE_NAME] 
                where [COLUMN_NAME] IN ( select max([COLUMN_NAME]) 
                                         from [TABLE_NAME] 
                                       )
                

                【讨论】:

                  【解决方案13】:
                  select max(COL_NAME) 
                  from TABLE_NAME 
                  where COL_NAME in ( select COL_NAME 
                                      from TABLE_NAME 
                                      where COL_NAME < ( select max(COL_NAME) 
                                                         from TABLE_NAME
                                                        )
                                     );
                  

                  子查询返回除最大值之外的所有值。 从返回的列表中选择最大值。

                  【讨论】:

                    【解决方案14】:
                    select min(sal) from emp where sal in 
                        (select TOP 2 (sal) from emp order by sal desc)
                    

                    注意

                    sal 是列名
                    emp 是表名

                    【讨论】:

                      【解决方案15】:
                      SELECT MAX(col) 
                      FROM table 
                      WHERE col NOT IN ( SELECT MAX(col) 
                                         FROM table
                                       );
                      

                      【讨论】:

                        【解决方案16】:
                        select col_name
                        from (
                            select dense_rank() over (order by col_name desc) as 'rank', col_name
                            from table_name ) withrank 
                        where rank = 2
                        

                        【讨论】:

                          【解决方案17】:
                          
                          select * from (select ROW_NUMBER() over (Order by Col_x desc) as Row, Col_1
                              from table_1)as table_new tn inner join table_1 t1
                              on tn.col_1 = t1.col_1
                          where row = 2
                          

                          希望这有助于获取任何行的值.....

                          【讨论】:

                            【解决方案18】:
                            SELECT 
                                * 
                            FROM 
                                table 
                            WHERE 
                                column < (SELECT max(columnq) FROM table) 
                            ORDER BY 
                                column DESC LIMIT 1
                            

                            【讨论】:

                              【解决方案19】:

                              查找第二大值的非常简单的查询

                              SELECT `Column` 
                              FROM `Table` 
                              ORDER BY `Column` DESC 
                              LIMIT 1,1;
                              

                              【讨论】:

                                【解决方案20】:

                                您可以使用以下查询找到列的第二大值

                                SELECT *
                                FROM TableName a
                                WHERE
                                  2 = (SELECT count(DISTINCT(b.ColumnName))
                                       FROM TableName b WHERE
                                       a.ColumnName <= b.ColumnName);
                                

                                您可以在以下链接中找到更多详细信息

                                http://www.abhishekbpatel.com/2012/12/how-to-get-nth-maximum-and-minimun.html

                                【讨论】:

                                【解决方案21】:

                                查询以查找连续第二高的数字-

                                select Top 1 (salary) from XYZ
                                where Salary not in (select distinct TOP 1(salary) from XYZ order by Salary desc)
                                ORDER BY Salary DESC
                                

                                通过将突出显示的Top 1 更改为TOP 234,您可以分别找到第三、第四和第五高。

                                【讨论】:

                                  【解决方案22】:

                                  我们还可以使用 order by 和 top 1 元素,如下所示:

                                  Select  top 1 col_name from table_name
                                  where col_name < (Select top 1 col_name from table_name order by col_name desc)
                                  order by col_name desc 
                                  

                                  【讨论】:

                                    【解决方案23】:
                                    SELECT * FROM EMP
                                    WHERE salary=
                                            (SELECT MAX(salary) FROM EMP
                                               WHERE salary != (SELECT MAX(salary) FROM EMP)
                                            );
                                    

                                    【讨论】:

                                      【解决方案24】:

                                      这是另一种查找列的第二大值的方法。考虑表'Student'和列'Age'。那么查询是,

                                      select top 1 Age 
                                      from Student 
                                      where Age in ( select distinct top 2 Age  
                                                     from Student order by Age desc 
                                                   ) order by Age asc
                                      

                                      【讨论】:

                                        【解决方案25】:

                                        这是最简单的方法:

                                        SELECT
                                              Column name
                                        FROM
                                              Table name 
                                        ORDER BY 
                                              Column name DESC
                                        LIMIT 1,1
                                        

                                        【讨论】:

                                          【解决方案26】:

                                          试试:

                                          select a.* ,b.* from 
                                          (select * from (select ROW_NUMBER() OVER(ORDER BY fc_amount desc) SrNo1, fc_amount as amount1 From entry group by fc_amount) tbl where tbl.SrNo1 = 2) a
                                          ,
                                          (select * from (select ROW_NUMBER() OVER(ORDER BY fc_amount asc) SrNo2, fc_amount as amount2  From entry group by fc_amount) tbl where tbl.SrNo2 =2) b
                                          

                                          【讨论】:

                                            【解决方案27】:
                                            select * from [table] where (column)=(select max(column)from [table] where column < (select max(column)from [table]))
                                            

                                            【讨论】:

                                              【解决方案28】:

                                              使用这个查询。

                                              SELECT MAX( colname ) 
                                              FROM Tablename 
                                              where colname < (
                                                  SELECT MAX( colname ) 
                                                  FROM Tablename)
                                              

                                              【讨论】:

                                              • 这个答案与@Matt Rogish 6 年前发布的答案相同,并且早已被标记为正确。这个答案没有添加任何内容,应该删除。
                                              【解决方案29】:
                                              select MAX(salary) as SecondMax from test where salary !=(select MAX(salary) from test)
                                              

                                              【讨论】:

                                                【解决方案30】:
                                                select age 
                                                from student 
                                                group by id having age< ( select max(age) 
                                                                          from student 
                                                                        )
                                                order by age 
                                                limit 1
                                                

                                                【讨论】:

                                                  猜你喜欢
                                                  • 1970-01-01
                                                  • 1970-01-01
                                                  • 2023-02-05
                                                  • 1970-01-01
                                                  • 2022-10-26
                                                  • 1970-01-01
                                                  • 2011-12-22
                                                  • 2021-12-17
                                                  相关资源
                                                  最近更新 更多