如果条件为true,则获取MIN(),否则获取下一个SQL

时间:2018-08-31 18:33:16

标签: sql

我有一个名为“事件”的表,并希望在“ created_at”日期之前获取第一个条目。但是,如果第一个事件(MIN(events.created_at))的标题包含“ test”,则我想返回该用户的下一个事件(由created_at决定)。如果用户只有一个事件,则只需返回该事件。

有没有一种简单的方法可以通过查询执行此操作?

这是我所能获得的。它通过created_at

返回第一个事件
SELECT MIN(events.created_at) 'event_created_at', events.user_id, events.title, MIN(events.type) 'type'
FROM events
GROUP BY events.user_id

这是用于SQL DBMS

3 个答案:

答案 0 :(得分:2)

我认为您确实想要有关该事件的完整信息。如果是这样,GROUP BY是错误的方法。

select e.*
from (select e.*,
             row_number() over (partition by e.user_id
                                order by (case when e.title not like '%test%' then 1 else 2 end) desc,
                                         e.created_at asc
                               ) as seqnum
      from events e
     ) e
where seqnum = 1;

当您要从组中选择行时,通常使用窗口函数比group by更好。

答案 1 :(得分:0)

对于SQL Server,WITH TIES将是一个不错的选择

select top 1 with ties
   events.user_id
   ,events.title
   ,events.created_at
   ,events.type
from events
order by row_number() over (partition by events.user_id order by case when events.title = 'test' then 2 else 1 end, events.created_at)

答案 2 :(得分:0)

编辑:戈登击败了我。在发布答案之前,请教我不要刷新。我同意,但是要使用Window Function。我和他的唯一的区别是检查NULL created_at日期。

SQL Fiddle

MS SQL Server 2017架构设置

CREATE TABLE events ( user_id int, title varchar(20), type varchar(20), created_at datetime ) ;

INSERT INTO events ( user_id, title, type, created_at )
VALUES 
    ( 1, 'Event1', 'Event', '2018-01-01 00:00:00.000' ) /* This one */
  , ( 2, 'Event1', 'Event', '2018-05-01 00:00:00.000' )
  , ( 2, 'Event1', 'Event', '2018-06-01 00:00:00.000' )
  , ( 1, 'Event2', 'Event', '2018-11-22 00:00:00.000' )
  , ( 5, 'Event2', 'test', '2018-11-22 00:00:00.000' )
  , ( 5, 'Event2', 'Event', '2018-01-02 00:00:00.000' ) /* This one */
  , ( 5, 'Event3', 'TesT', '2018-01-03 00:00:00.000' )
  , ( 5, 'Event3', 'NoTest', '2018-01-03 00:00:00.000' ) /* This one */
  , ( 4, 'Event3', 'test', '2018-01-01 00:00:00.000' )
  , ( 1, 'Event4', 'TeSt', '2018-01-04 00:00:00.000' ) /* This one */
  , ( 2, 'Event5', 'Event', null )
  , ( 3, 'Event5', 'Event', '2018-01-05 00:00:00.000' ) /* This one */
  , ( 4, 'Event6', 'test', '2018-01-07 00:00:00.000' ) 
  , ( 4, 'Event6', 'test', '2018-01-06 00:00:00.000' ) /* This one */
 ;

主要查询

SELECT s1.created_at AS event_created_at
  , s1.user_id
  , s1.title
  , s1.type
FROM (
  SELECT e.title, e.user_id, e.type, e.created_at
    , ROW_NUMBER() OVER ( 
        PARTITION BY e.title
        ORDER BY e.title, CASE WHEN e.type='test' THEN 1 ELSE 2 END DESC, e.created_at
      ) AS rn
  FROM events e
  WHERE e.created_at IS NOT NULL
) s1
WHERE s1.rn = 1

Results

|     event_created_at | user_id |  title |   type |
|----------------------|---------|--------|--------|
| 2018-01-01T00:00:00Z |       1 | Event1 |  Event |
| 2018-01-02T00:00:00Z |       5 | Event2 |  Event |
| 2018-01-03T00:00:00Z |       5 | Event3 | NoTest |
| 2018-01-04T00:00:00Z |       1 | Event4 |   TeSt |
| 2018-01-05T00:00:00Z |       3 | Event5 |  Event |
| 2018-01-06T00:00:00Z |       4 | Event6 |   test |