【问题标题】:MySQL finding gaps in column with multiple IDMySQL在具有多个ID的列中查找间隙
【发布时间】:2016-04-30 14:35:54
【问题描述】:

我想在下表中找出差距:

create table sequence
(
   `Id` int,
   `Value` int not null,
   PRIMARY KEY (`Id`,`Value`)
);

insert into sequence
    ( `Id`, `Value` )
  values
    (10, 0 ),
    (10, 1 ),
    (10, 4 ),
    (10, 5 ),
    (10, 6 ),
    (10, 7 ),
    (11, 0 ),
    (11, 1 ),
    (11, 2 ),
    (11, 5 ),
    (11, 7 );

预期的结果是这样的:

10 | 2-3
11 | 3-4
11 | 6

10 | 2
10 | 3
11 | 3
11 | 4
11 | 6

我知道,'Value' 列的值在 0 到 7 之间。

是否可以使用 MySQL 来做到这一点?

编辑 1

根据我得出的答案:

SELECT Tbl1.Id, 
       startseqno, 
       Min(B.Value) - 1 AS END 
FROM   (SELECT Id, 
               Value + 1 AS StartSeqNo 
        FROM   SEQUENCE AS A 
        WHERE  NOT EXISTS (SELECT * 
                           FROM   SEQUENCE AS B 
                           WHERE  B.Id = A.id 
                                  AND B.Value = A.Value + 1) 
               AND Value < (SELECT Max(Value) 
                            FROM   SEQUENCE B 
                            WHERE  B.Id = A.Id)) AS Tbl1, 
       SEQUENCE AS B 
WHERE  B.Id = Tbl1.Id 
       AND B.Value > Tbl1.startseqno 

但现在我得到的只是

10 | 2 | 3

请问有人知道如何解决吗?

sqlfiddle

【问题讨论】:

标签: mysql sql database gaps-in-data


【解决方案1】:

您可以使用not exists

select s.*
from sequence s
where not exists (select 1 from sequence s2 where s2.id = s.id and s2.value = s.value + 1) and
      exists (select 1 from sequence s2 where s2.id = s.id and s2.value > s.value);

exists 子句很重要,因此您不必报告每个 id 的最终值。

编辑:

这是一个更好的方法:

select s.value + 1 as startgap,
       (select min(s2.value) - 1 from sequence s2 where s2.id = s.id and s2.value > s.value) as endgap
from sequence s
where not exists (select 1 from sequence s2 where s2.id = s.id and s2.value = s.value + 1) and
      exists (select 1 from sequence s2 where s2.id = s.id and s2.value > s.value);

【讨论】:

  • 感谢您的回答,但我还需要每个间隙的结尾。是否可以扩展此命令以包含它?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-04-07
  • 1970-01-01
  • 2021-01-27
  • 2021-09-07
相关资源
最近更新 更多