gpt4 book ai didi

sql - PostgreSQL 11.2 按单个表中的公共(public)属性对对象进行分组

转载 作者:行者123 更新时间:2023-12-04 10:01:33 25 4
gpt4 key购买 nike

我在一个网络数据集上工作(使用 PostGIS 扩展,但是由于我当前使用 pgrouting 的方法是我发现的唯一一种可以做我想做的事情并且运行起来非常痛苦,我想尝试通过属性来处理它),例如下图:
enter image description here

每个部分(字母)是一个单独的对象,颜色是对象的相关属性。

表示此的表定义如下:

CREATE TABLE lines (gid text, color text, startpoint integer, endpoint integer);
INSERT INTO lines (gid, color, startpoint, endpoint)
VALUES
('A','green', 1, 2),
('B','green', 2, 3),
('C','green', 3, 4),
('D','green', 4, 5),
('E','red', 2, 6),
('F','red', 6, 7),
('G','red', 7, 8),
('H','blue', 3, 9),
('I','blue', 4, 10),
('J','blue', 10, 11);

我想要得到的结果是一个由所有相同颜色的对象相互接触组成的聚合对象。所以这里有 4 个对象:{A,B,C,D}, {E,F,G}, {H} 和 {I,J}。我假设要走的路是使用起点和终点值,因为它们决定了对象的接触方面。

现在我像下面的代码一样,使用 JOIN因此返回对象 H(如果我使用与 WHERE 条件相同的 ON 子句,则不会返回 H,因为它永远不会匹配起点/终点相关性):
SELECT a.gid, b.gid, a.color 
FROM lines a
LEFT JOIN lines b ON a.gid > b.gid AND (a.startpoint = b.endpoint OR a.endpoint = b.startpoint) AND a.color = b.color

有了这个结果:

enter image description here

从这里我不知道该怎么做。我在 PostGIS 中使用聚合函数来合并行,所以我想我需要以这种形式获得结果(这样我就可以使用 GROUP BY 运行查询):

enter image description here

有人会知道一种方法来做我想做的事吗?

最佳答案

假设您的数据没有圆圈,如示例数据所示,一个选项是使用递归查询。

这个想法是首先确定每种颜色的所有起点。为此,您可以使用 not exsits :

select l.*
from lines l
where not exists (
select 1 from lines l1 where l1.endpoint = l.startpoint and l1.color = l.color
)

从那里开始,您可以递归地遍历结构,通过查找从前一个结束的位置开始的相同颜色的线条,同时跟踪数组中的线条路径。

最后一步是过滤结果集以识别非重叠路径。为此,我们可以使用 not exists与收容运算符(operator)。

请注意,此技术允许分支(如果有)。

代码:
with recursive cte as (
select l.*, array[gid] path
from lines l
where not exists (
select 1 from lines l1 where l1.endpoint = l.startpoint and l1.color = l.color
)
union all
select l.*, c.path || l.gid
from cte c
inner join lines l on l.startpoint = c.endpoint and l.color = c.color
)
select color, path
from cte c
where not exists (select 1 from cte c1 where c1.path @> c.path and not c.path @> c1.path)
order by color, path

Demo on DB Fiddle :

颜色 |小路
:---- | :--------
蓝色 | {H}
蓝色 | {我,J}
绿色 | {A B C D}
红色 | {E,F,G}

关于sql - PostgreSQL 11.2 按单个表中的公共(public)属性对对象进行分组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/61802026/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com