【问题标题】:set based approach to remove contained points基于集合的方法来删除包含的点
【发布时间】:2015-09-19 18:07:04
【问题描述】:

我有这些数据:

IF OBJECT_ID('tempdb..#temp') IS NOT NULL
    DROP TABLE #temp
CREATE TABLE #temp
    (
      Id INT IDENTITY(1, 1) ,
      X FLOAT NOT NULL ,
      Y FLOAT NOT NULL
    )

INSERT INTO #temp (X, Y) VALUES (0, 0)
INSERT INTO #temp (X, Y) VALUES (0, 1)
INSERT INTO #temp (X, Y) VALUES (0, 2)
INSERT INTO #temp (X, Y) VALUES (0.5, 1)
INSERT INTO #temp (X, Y) VALUES (1, 1)
INSERT INTO #temp (X, Y) VALUES (1, 2)
INSERT INTO #temp (X, Y) VALUES (1.5, 0.5)
INSERT INTO #temp (X, Y) VALUES (2, 0)
INSERT INTO #temp (X, Y) VALUES (2, 1)

我想删除包含在其他点中的点,例如:

(0, 1)
(1, 1)
(1.5, 0.5)

获取定义外部多边形的最外部点,该外部多边形仅由垂直和水平线组成,没有冗余(例如,(0, 1) 是冗余点)。这可以通过 SQL Server 2014 中基于集合的 TSQL 方法来实现吗?

PS:

数据的散点图如下:

我想删除被包围的点。最终,我在外边界之后(绘制为红线)。希望这能让它更清楚。

【问题讨论】:

  • 那么想要的结果是什么?
  • 对不起,如果我不清楚。删除点:(0, 1), (1, 1), (1.5, 0.5)
  • 问题不明确,因为相同的点可以创建另一个多边形。例如,您可以将 (1,2) 与 (1.5,.5) 连接,然后与 (2,1) 连接,这将包含点 (1,1) 而不是 (1.5,.5)。
  • @ughai:他只想要最外层多边形的顶点。
  • ughai 是正确的,据我所知,该问题尚未得到解答。 (1,2)连接到(2,1)的多边形呢?这可以被认为是“最外层的”。我们是说仅由水平线和垂直线组成的凸多边形吗?

标签: sql-server tsql sql-server-2014


【解决方案1】:

我相信这可能会奏效。它似乎可以交付您的测试数据。 有点粗糙。如果您的实际数据很大,一些 SELECT MIN 和 SELECT MAX 可能会提前计算出来。

SELECT * 
-- uncomment this to delete the desired points
-- DELETE #temp
FROM #temp t
WHERE 
(
    -- Internal points
    (
            ( X > (SELECT MIN(X) FROM #temp) AND X < (SELECT MAX(X) FROM #temp) )
        AND ( Y > (SELECT MIN(Y) FROM #temp) AND Y < (SELECT MAX(Y) FROM #temp) )
    )
    -- Exceptions (points with nothing strictly outside them) [Don't want to lose (1,1)]
    AND EXISTS (SELECT * FROM #temp WHERE X > t.X AND Y > t.Y)
)
OR
    -- redundant edge points [(0,1) would be included as an "exception"]
(
    ( (t.X = (SELECT MIN(X) FROM #temp) OR t.X = (SELECT MAX(X) FROM #temp)) 
        AND EXISTS (SELECT * FROM #temp WHERE X = t.X AND Y > t.Y) 
        AND EXISTS (SELECT * FROM #temp WHERE X = t.X AND Y < t.Y)  )
    OR
    ( (t.Y = (SELECT MIN(Y) FROM #temp) OR t.Y = (SELECT MAX(Y) FROM #temp)) 
        AND EXISTS (SELECT * FROM #temp WHERE Y = t.Y AND X > t.X) 
        AND EXISTS (SELECT * FROM #temp WHERE Y = t.Y AND X < t.X)  )
)

【讨论】:

  • 抱歉,刚刚试了,还是不行。它只返回 3 分而不是 6。
  • 感谢这实际上适用于给定的示例。所以我会接受这个。谢谢。
猜你喜欢
  • 1970-01-01
  • 2020-12-25
  • 1970-01-01
  • 1970-01-01
  • 2012-08-24
  • 2012-01-24
  • 1970-01-01
  • 2013-03-07
  • 2020-07-29
相关资源
最近更新 更多