[postgis-users] Split polygons based on polygons' area
Darafei "Komяpa" Praliaskouski
me at komzpa.net
Tue Jun 19 03:16:00 PDT 2018
Hi,
The problem in your query is that it doesn't unnest/ST_Dump some
intermediate states. Here's working one:
drop table if exists split_parkings;
create table split_parkings as (
with
input as (
select
ref as poly_id,
geom as geom
from
juno_areas
where type = 'airport_parking_lot'
),
unlabeled_cloud as (
select
poly_id,
geom,
(ST_Dump(ST_GeneratePoints(geom, 1000))).geom pt,
(ST_Area(geom) / 1000) :: int k
from input
group by 1, 2
order by geom
),
labeled_cloud as (
select
poly_id,
pt,
ST_ClusterKMeans(pt, k)
over (
partition by poly_id
) cluster_id
from
unlabeled_cloud
),
labeled_centers as (
select
poly_id,
cluster_id,
ST_Centroid(ST_Collect(pt)) center
from labeled_cloud
group by poly_id, cluster_id),
voronoi_poly as (
select
poly_id,
(ST_Dump(ST_VoronoiPolygons(ST_Collect(center)))).geom
from labeled_centers
group by poly_id
)
select v.poly_id, ST_Intersection(v.geom, i.geom)
from voronoi_poly v join input i on i.poly_id = v.poly_id);
Produces:
[image: image.png]
Trivial ones are split this way:
[image: image.png]
Good luck!
вс, 17 июн. 2018 г. в 17:55, Jibran Khan <jibran at envs.au.dk>:
> Hi,
>
>
>
> Thanks a lot for your help. Here is my first attempt.
>
>
>
> /*## Start ##*/
>
> With foo as(
>
> Select
>
> gid poly_id, geom,
>
> ST_GeneratePoints(geom, 1000) ptcloud,
>
> (ST_Area(geom)/100)::int k
>
> From
>
> My_polygon_shp
>
> Group by gid, geom
>
> Order by gid, geom),
>
>
>
> bar as(
>
> Select
>
> poly_id, geom, ptcloud,
>
> ST_VoronoiPolygons(ST_Centroid(ST_Collect(ptcloud)))
> vorpoly,
>
> ST_ClusterKMeans(ptcloud, k) over() kmeans
>
> From
>
> foo
>
> Group by poly_id, geom, ptcloud, k
>
> Order by poly_id)
>
>
>
> Select
>
> poly_id,
>
> st_intersection(geom, vorpoly)
>
> From
>
> bar
>
> Order by poly_id
>
> /*## End ##*/
>
>
>
> The query may not be efficiently written but it works. However, I don’t
> get any significant result.
>
> Please see if you can you reproduce the same error or above query can be
> improved?
>
>
>
> Best,
>
> Jb
>
>
>
> *From:* postgis-users <postgis-users-bounces at lists.osgeo.org> *On Behalf
> Of *Darafei "Kom?pa" Praliaskouski
> *Sent:* 17. juni 2018 12:26
> *To:* PostGIS Users Discussion <postgis-users at lists.osgeo.org>
> *Subject:* Re: [postgis-users] Split polygons based on polygons' area
>
>
>
> The way I see it, for any kind of polygon:
>
> - Convert a polygon to a set of points proportional to the area by
> ST_GeneratePoints (the more points, the more beautiful it will be, guess
> 1000 is ok);
>
> - Decide how many parts you'd like to split into,
> (ST_Area(geom)/max_area), let it be K;
> - Take KMeans of the point cloud with K clusters;
>
> - For each cluster, take a ST_Centroid(ST_Collect(point));
>
> - Feed these centroids into ST_VoronoiPolygons, that will get you a mask
> for each part of polygon;
> - ST_Intersection of original polygon and each cell of Voronoi polygons
> will get you a good split of your polygon into K parts.
>
> Will it work for you?
>
>
>
> вс, 17 июн. 2018 г. в 13:11, Jibran Khan <jibran at envs.au.dk>:
>
> Hello everyone,
>
>
>
> I need some help in terms of splitting polygons based on the polygon area.
> I am using PostgreSQL 9.5.12/PostGIS 2.3 on Windows 10 (x64). I have two
> tables i.e. polygon (poly) and points (pts) in my Postgres db. Some of the
> polygons contain points inside them while, some do not (sample scenario
> below):
>
>
>
>
>
> The following query:
>
>
>
> /*Start of query*/
>
> Select
>
> a.gid poly_id, count(b.geom) pt_cnt,
>
> st_area(a.geom)::int poly_area
>
> FROM
>
> poly a
>
> LEFT JOIN
>
> pts b
>
> ON st_contains(a.geom, b.geom)
>
> GROUP BY a.gid
>
> Order by a.gid;
>
> /*End of query*/
>
>
>
> Returns the area of polygons (from left to right) as 1079, 744, 340
> square-meter, respectively. I need to split these polygons' geometry based
> on the area i.e. if area is above 100 meter-square, then each polygon needs
> to be divided/split into “approximate equal” parts (assuming that majority
> of the polygons are *straightforward* like above). The division does not
> have to be “strictly” equal. Does anyone know or have any idea how this can
> be achieved?
>
>
>
> *Side Notes:*
>
>
>
> · I earlier posted this question here at GIS SE
> <https://gis.stackexchange.com/questions/286184/postgis-how-do-i-split-polygon-in-equal-parts-based-on-polygon-area>
>
> · Also, came across this
> <https://gis.stackexchange.com/questions/239801/how-can-i-split-a-polygon-into-two-equal-parts-along-a-n-s-axis>
> relevant question but I guess my problem is different
>
>
>
> Any help or idea(s) would be highly appreciated.
>
>
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.osgeo.org/pipermail/postgis-users/attachments/20180619/0ad7d688/attachment.html>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: image.png
Type: image/png
Size: 43431 bytes
Desc: not available
URL: <http://lists.osgeo.org/pipermail/postgis-users/attachments/20180619/0ad7d688/attachment.png>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: image.png
Type: image/png
Size: 29585 bytes
Desc: not available
URL: <http://lists.osgeo.org/pipermail/postgis-users/attachments/20180619/0ad7d688/attachment-0001.png>
More information about the postgis-users
mailing list