【问题标题】:SELECT First Group选择第一组
【发布时间】:2015-08-21 15:44:16
【问题描述】:

问题定义

我有一个如下所示的 SQL 查询:

SELECT *
    FROM table
    WHERE criteria = 1
    ORDER BY group;

结果

我明白了:

group | value | criteria
------------------------
  A   |  0    |   1
  A   |  1    |   1
  B   |  2    |   1
  B   |  3    |   1

预期结果

但是,我想将结果限制在第一组(在本例中为 A)。即,

group | value | criteria
------------------------
  A   |  0    |   1
  A   |  1    |   1

我尝试过的

分组方式

SELECT *
    FROM table
    WHERE criteria = 1
    GROUP BY group;

我可以使用GROUP BY 子句聚合组,但这会给我:

group | value
-------------
  A   |  0
  B   |  2

或每个组的某些聚合函数。但是,我不想聚合这些行!

子查询

我也可以通过子查询指定分组:

SELECT *
  FROM table
 WHERE criteria = 1 AND 
       group = (
                       SELECT group
                         FROM table
                        WHERE criteria = 1
                        ORDER BY group ASC
                        LIMIT 1
                   );

这行得通,但一如既往,子查询很混乱。特别是,这需要为criteria 指定我的WHERE 子句两次。当然必须有一种更清洁的方法来做到这一点。

【问题讨论】:

    标签: sql sqlite subquery correlated-subquery


    【解决方案1】:

    您可以尝试以下查询:-

    SELECT *
    FROM table
    WHERE criteria = 1
    AND group = (SELECT MIN(group) FROM table)
    ORDER BY value;
    

    【讨论】:

    • 我认为他想要的是符合他标准的第一组,而不是总体上的第一组。
    【解决方案2】:

    如果你的数据库支持 WITH 子句,试试这个。它类似于使用子查询,但您只需要指定一次criteria 输入。也更容易理解发生了什么。

    with main_query as (
      select *
      from table
      where criteria = 1
      order by group, value
    ),
    with min_group as (
      select min(group) from main_query
    )
    select *
    from main_query
    where group in (select group from min_group);
      -- this where clause should be fast since there will only be 1 record in min_group
    

    【讨论】:

      【解决方案3】:

      使用 DENSE_RANK()

      DECLARE @yourTbl AS TABLE (
          [group] NVARCHAR(50),
          value INT,
          criteria INT
      )
      
      INSERT INTO @yourTbl VALUES ( 'A', 0, 1 )
      INSERT INTO @yourTbl VALUES ( 'A', 1, 1 )
      INSERT INTO @yourTbl VALUES ( 'B', 2, 1 )
      INSERT INTO @yourTbl VALUES ( 'B', 3, 1 )
      
      ;WITH cte AS
      (
         SELECT i.* , 
         DENSE_RANK() OVER (ORDER BY i.[group]) AS gn
         FROM @yourTbl AS i
         WHERE i.criteria = 1
      )
      SELECT *
      FROM cte
      WHERE gn = 1
      
      
      group | value | criteria
      ------------------------
      A     | 0     | 1     
      A     | 1     | 1   
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2012-10-28
        • 2015-11-28
        • 2014-01-17
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多