如果某些列值在SQL中直接在另一个列之后进行分组行

时间:2011-11-24 10:22:24

标签: sql sql-server

我正在使用MS SQL Server 2008,我希望如此:

+------+--------+--------+------------+
| id   | Name   | Event  | Timestamp  |
+------+--------+--------+------------+
|    0 | bob    | note   | 14:20      |
|    1 | bob    | time   | 14:22      |
|    2 | bob    | time   | 14:40      |
|    3 | bob    | time   | 14:45      |
|    4 | bob    | send   | 14:48      |
|    5 | bob    | time   | 15:30      |
|    6 | bob    | note   | 15:35      |
|    7 | bob    | note   | 18:00      |
+------+--------+--------+------------+

成为这个:

+------+--------+--------+------------+
| id   | Name   | Event  | Timestamp  |
+------+--------+--------+------------+
|    0 | bob    | note   | 14:20      |
|    1 | bob    | time   | 14:22      |
|    4 | bob    | send   | 14:48      |
|    5 | bob    | time   | 15:30      |
|    6 | bob    | note   | 15:35      |
+------+--------+--------+------------+

即,行由“事件”列“分组”。每个分组相同的“事件”中只有一个会被显示出来。

  • 如果有一个事件,例如“注意”与id 0一样,在表中没有直接在它之前或之后的行(具有最近时间戳的行)具有相等的“事件”值,它显示;
  • 如果多个行具有相同的事件,例如与时间1-3一样的“时间”。在彼此之后(即没有具有不同“事件”的行具有“在它们之间”的时间戳),显示它们中的任何一个(对我来说无关紧要,所有其他列无论如何都是相同的)。

这两个是唯一的规则。

1 个答案:

答案 0 :(得分:3)

如果id是一个接一个,请尝试这样做:

select * into #tab from(
    select 0 as id, 'bob' as name, 'note' as event, '14:20' as time union
    select 1, 'bob', 'time', '14:22' union
    select 2, 'bob', 'time', '14:40' union
    select 3, 'bob', 'time', '14:45' union
    select 4, 'bob', 'send', '14:48' union
    select 5, 'bob', 'time', '15:30' union
    select 6, 'bob', 'note', '15:35' union
    select 7, 'bob', 'note', '18:00'
) t

select t.*
from #tab t
left join #tab t1 on t.id = t1.id + 1 and t1.event = t.event 
    -- and t1.name = t.name -- if there are more names you are going to need this one as well
where t1.id is null

结果:

id  name    event   time
0   bob     note    14:20
1   bob     time    14:22
4   bob     send    14:48
5   bob     time    15:30
6   bob     note    15:35

<强>加了:

如果id不是一个接一个,你可以将它们变为:

select identity(int, 1, 1) as id, name, event, time 
into #tab_ordered_ids
from #tab order by name, id, time