0

次のようなテーブルがあります。

eventId    activity    timestamp
1          0           2012-10-22 20:10:00
2          0           2012-10-22 20:10:20
3          1           2012-10-22 20:11:25
4          1           2012-10-22 20:12:20
5          1           2012-10-22 20:12:22
6          0           2012-10-22 20:12:30  <--
7          1           2012-10-22 20:12:25  <--
8          0           2012-10-22 20:14:46
9          0           2012-10-22 20:14:48
10         1           2012-10-22 20:15:45
11         0           2012-10-22 20:16:00
12         0           2012-10-22 20:17:00
13         0           2012-10-22 20:17:13

アクティビティが0で、アクティビティ1の行の横に時系列でないすべての行を削除したいので、この例から、eventID 1、8、12、および13の行を削除します。行6および7に示すように、非同期でテーブルに挿入されます。

個々の行をチェックし、クエリを発行して条件に一致する場合は削除することで、これをループで実行できることはわかっていますが、これは非常に非効率的です。これをすべて1つのクエリで実行できるかどうか疑問に思いました。

似たようなことができたら

delete from mytable
where activity = 0
and (rownumber()+1).activity = 0
and (rownumber()-1).activity = 0
order by timestamp

これは簡単ですが、そのような機能は不可能だと思います。

4

1 に答える 1

2

保持したいすべてのレコードを選択する方法は次のとおりです。

select m.eventId
from (
  select t1.eventId, 
      max(t2.timestamp) as previousTime,
      min(t3.timestamp) as nextTime
  from mytable t1
  left outer join mytable t2 on t1.eventId <> t2.eventId and t2.timestamp < t1.timestamp
  left outer join mytable t3 on t1.eventId <> t3.eventId and t3.timestamp > t1.timestamp
  group by t1.eventId
) m
left outer join mytable tb on m.previousTime = tb.timestamp
left outer join mytable ta on m.nextTime = ta.timestamp
where tb.activity = 1
    or ta.activity = 1

SQL フィドルの例

次に、次のようなことができます。

delete from mytable
where mytable.eventId not in ( ... ) <--above query
于 2012-11-07T02:07:37.240 に答える