【问题标题】:Look for overlapping in a table在表中查找重叠
【发布时间】:2022-01-10 05:21:55
【问题描述】:

我在 SQL Server 中有一个存储地毯的表。每个都有自己的 ID,以及以米为单位(从到到)的范围和颜色。

CREATE TABLE rugs (
  [code] VARCHAR (10), 
  [from] INT, 
  [to] INT,
  [color] VARCHAR (10)
);

INSERT INTO rugs VALUES ('RUG001', 0, 1, 'Yellow');
INSERT INTO rugs VALUES ('RUG001', 1, 2, 'Red');
INSERT INTO rugs VALUES ('RUG001', 2, 4, 'Blue');
INSERT INTO rugs VALUES ('RUG001', 3, 5, 'Green');
INSERT INTO rugs VALUES ('RUG002', 0, 1, 'Purple');
INSERT INTO rugs VALUES ('RUG002', 1, 2, 'Orange');

在此示例中,它在对应于地毯 RUG001 的蓝色和绿色的行中重叠。 RUG002 没问题。

如何检查同一张地毯是否有重叠的间隔?

我尝试了什么(但它不起作用)

Select * from RUGS as R1
INNER JOIN RUGS as R2
ON R1.CODE = R2.CODE
WHERE
R1.[FROM] <= R2.[TO] AND R1.[TO] >= R2.[FROM]

【问题讨论】:

  • ..WHERE R1.[from] &lt; R2.[to] AND R1.[to] &gt; R2.[from] and not(R1.[from] = R2.[from] and R1.[to] = R2.[to] and R1.color = R2.color)

标签: sql sql-server tsql


【解决方案1】:

对于小型数据集很难确定,但以下内容对您有用吗?使用 Lead/Lag 检查下一个或最后一个范围是否在当前范围内。

with rug as (
select * ,
    Lead([from]) over(partition by code order by [from]) nextfrom, 
    Lag([to]) over(partition by code order by [to]) lastto
from rugs
)
select code, [from], [to], color 
from rug
where nextfrom<[to] or lastto>[from]

【讨论】:

    【解决方案2】:

    这里有两种可能的解决方案。

    1. 只是左侧重叠:
    SELECT * FROM RUGS R1
    INNER JOIN RUGS R2 ON R1.CODE = R2.CODE
    WHERE R1.[TO] < R2.[TO] AND R2.[FROM] < R1.[TO] 
    
    --Result
    /*
    code    from    to  color   code    from    to  color
    RUG001  2       4   Blue    RUG001  3       5   Green
    */
    
    1. 所有重叠:
    SELECT * FROM RUGS R1
    INNER JOIN RUGS R2 ON R1.CODE = R2.CODE
    WHERE R1.[FROM] < R2.[FROM] AND R2.[TO] < R1.[TO] 
    OR (R2.[FROM] < R1.[FROM] AND  R2.[TO] < R1.[TO] AND R1.[FROM] < R2.[TO])
    OR (R1.[FROM] < R2.[FROM] AND  R1.[TO] < R2.[TO] AND R2.[FROM] < R1.[TO])
    
    -- Result
    /*
    code    from    to  color   code    from    to  color
    RUG001  2       4   Blue    RUG001  3       5   Green
    RUG001  3       5   Green   RUG001  2       4   Blue
    */
    

    【讨论】: