বহু-জ্যামিতি থেকে দ্রবীভূত বাফার তৈরি করুন (ভাগ করা বিশিষ্টতা এবং স্থানীয় ছেদ দ্বারা ইউনিয়ন)


10

আমি মাল্টি-পয়েন্ট ইনপুট বৈশিষ্ট্যগুলি থেকে দ্রবীভূত বাফারগুলি তৈরি করতে চাই। নীচের উদাহরণে ইনপুট টেবিলটিতে 4 টি বৈশিষ্ট্য রয়েছে। বৈশিষ্ট্য #2দুটি পয়েন্ট জ্যামিতি নিয়ে গঠিত। একটি বাফার তৈরির পরে, আমি 4 বহুভুজ জ্যামিতি পেয়েছি:

এখানে চিত্র বর্ণনা লিখুন

ফলাফলকে গ্রুপ করার কোনও উপায় আছে কি? পয়েন্ট বাফার #1এবং #2দ্রবীভূত করা হয় এবং একটি একক বহু-বহুভুজ বৈশিষ্ট্য হওয়া উচিত ( a)।

আমি এ পর্যন্ত কী করেছি:

-- collect all buffers to a single multi-polygon feature
-- dissolve overlapping polygon geometries
CREATE TABLE public.pg_multibuffer AS SELECT
    row_number() over() AS gid,
    sub_qry.*
FROM (SELECT
    ST_Union(ST_Buffer(geom, 1000, 8))::geometry(MultiPolygon, /*SRID*/) AS geom
FROM
public.multipoints)
AS sub_qry;

সম্পাদনা করুন:

-- create sample geometries

CREATE TABLE public.multipoints (
gid serial NOT NULL,
geom geometry(MultiPoint, 31256),
CONSTRAINT multipoints_pkey PRIMARY KEY (gid)
);

CREATE INDEX sidx_multipoints_geom
ON public.multipoints
USING gist
(geom);

INSERT INTO public.multipoints (gid, geom) VALUES
(1, ST_SetSRID(ST_GeomFromText('MultiPoint(12370 361685)'), 31256)),
(2, ST_SetSRID(ST_GeomFromText('MultiPoint(13520 360880, 19325 364350)'), 31256)),
(3, ST_SetSRID(ST_GeomFromText('MultiPoint(11785 367775)'), 31256)),
(4, ST_SetSRID(ST_GeomFromText('MultiPoint(19525 356305)'), 31256));

আপনি সাবকিউরিগুলি খুব বেশি ব্যবহার করেন। এটি আপনি যে বৈশিষ্ট্যে ক্লাস্টার করতে চান তার উপর ভিত্তি করে গ্রুপের আপনার ক্ষমতা হ্রাস করে।
ভিন্স

সুতরাং আপনাকে একটি স্থানিক ইউনিয়ন করতে হবে এবং তারপরে বৈশিষ্ট্য সংখ্যার উপর ভিত্তি করে একটি ইউনিয়নও করা উচিত, যার কারণে আপনি উপরের চিত্রটি থেকে 3 গুণকোষ আশা করে। আমার সন্দেহ হয় এটির জন্য একটি দ্বি-পদক্ষেপ প্রক্রিয়া প্রয়োজন, তবে কোনও উত্তর দেওয়ার আগে কেবল এই প্রশ্নে পরিষ্কার হতে চেয়েছিল।
জন পাওয়েল

হ্যাঁ, আমি বাফার বহুভুজগুলিকে ইউনিয়ন করতে এবং ইনপুট বৈশিষ্ট্যের সংখ্যার ভিত্তিতে ফলাফল সংগ্রহ করতে চাই।
eclipsed_by_the_moon

এ সম্পর্কে কোন আপডেট? আমি জানতে চাই যে এটি আপনার পক্ষে কাজ করে কিনা, যতদূর আমি দেখতে পাচ্ছি, আমি প্রশ্নের উত্তর দিয়েছি।
জন পাওয়েল

দেরিতে জবাবের জন্য দুঃখিত, আমি বেশ কয়েকদিন অনলাইনে নেই।
গ্রহন

উত্তর:


7

কয়েকটি এলোমেলো পয়েন্ট দিয়ে শুরু করে, ওপি-র চিত্রের অনুকরণের জন্য সত্যায়িতভাবে, যেখানে প্রথম দুটি স্থানিকভাবে ছেদ করে, তারপরে ২ য় এবং তৃতীয়র মধ্যে একই বৈশিষ্ট্য আইডি (২) রয়েছে, যা দুটি স্থানের সাথে ছেদ করতে পারে না বা হয় না একই বৈশিষ্ট্য, নিম্নলিখিত কোয়েরি 3 টি গুচ্ছ উত্পাদন করে:

WITH 
  temp (id, geom) AS 
     (VALUES (1, ST_Buffer(ST_Makepoint(0, 0), 2)),
        (2, ST_Buffer(ST_MakePoint(-0.7,0.5), 2)),
        (2, ST_Buffer(ST_MakePoint(10, 10), 2)), 
        (3, ST_Buffer(ST_MakePoint(-2, 12), 2)), 
        (4, ST_Buffer(ST_MakePoint(5, -6), 2))),
 unions(geoms) AS 
      (SELECT ST_Union(geom) FROM temp GROUP BY id),
 clusters(geoms) AS 
      (SELECT ST_CollectionExtract(unnest(ST_ClusterIntersecting(geoms)), 3) 
         FROM unions),
 multis(id, geoms) AS 
      (SELECT row_number() over() as id, geoms FROM clusters)
 SELECT ST_UNION(d.geom) FROM 
      (SELECT id, (ST_DUMP(geoms)).geom FROM multis) d GROUP BY id;

এখানে বেশ কয়েকটি পদক্ষেপ রয়েছে:

  1. ST_Unionআইডি দ্বারা গোষ্ঠীকরণ, বৈশিষ্ট্য দ্বারা প্রথম গোষ্ঠীতে ব্যবহার করুন
  2. ST_ClusterIntersectingএকই গ্রুপ থেকে যারা সংক্ষিপ্তভাবে ছেদ করে তাদের একত্রিত করতে ব্যবহার করুন
  3. প্রতিটি ক্লাস্টারে একটি আইডি যুক্ত করুন (টেবিল মাল্টিস) - এটি সরাসরি ক্লাস্টার ইন্টারেক্টেটিংয়ে করার চেষ্টা করে সমস্ত জ্যামিতিগুলিকে 1 এর আইডি পেয়ে যায়
  4. পদক্ষেপ 2 থেকে ফেলে দেওয়া জ্যামিতিগুলি ইউনিয়ন করুন, পদক্ষেপ 3 থেকে আইডি দ্বারা গোষ্ঠীকরণ করুন - এটি দ্রবীভূত অংশ। এটি আপনার ক্লাস্টার A তে দুটি ওভারল্যাপিং বহুভুজকে ওভারল্যাপিংয়ের পরিবর্তে একত্রে যোগদান করার কারণ হিসাবে এগুলি দ্বিতীয় ধাপের শেষে রয়েছে।

বরং দীর্ঘ, তবে এটি কার্যকর হয় (এবং, আমি নিশ্চিত যে আরও একটি ছোট উপায় আছে)।

কিউজিআইএস-এ ডব্লিউকেটি সরঞ্জামটি ব্যবহার করে, (এবং আমি সম্পাদনার সরঞ্জামগুলির সাথে আমি কতটা ভয়ঙ্কর তা আবিষ্কার করছি) নীচের মতো ক্লাস্টার তৈরি করে, যেখানে আপনি ক্লাস্টারটিকে একটি হিসাবে লেবেলযুক্ত দেখতে পাচ্ছেন, সব মিলিয়ে রয়েছে - অর্থাত্ একটি বর্ণ।

এখানে চিত্র বর্ণনা লিখুন

আপনি যদি ফাইনালের জন্য একটি ST_AsText রাখেন, ST_UNION (d.geom), তবে আপনি ফলাফলগুলি সরাসরি দেখতে পাবেন।

মন্তব্যে আরও তথ্যের অনুসরণ করে সম্পাদনা করুন: আপনি যখন পয়েন্টগুলি শুরু করছেন আপনাকে বাফারটি আমার মূল সমাধানটিতে অন্তর্ভুক্ত করতে হবে - যা আমি আপনার চিত্রটি নকল করতে শুরুতে অস্থায়ী সিটিইতে রেখেছি। ইউনিয়ন সিটিইতে বাফার যুক্ত করা আরও সহজ হবে, তাই আপনি একবারে সমস্ত জ্যামিতি করতে পারেন। সুতরাং, উদাহরণস্বরূপ, 1000 এর বাফার দূরত্ব ব্যবহার করে, নিম্নলিখিত এখন 3 টি ক্লাস্টার প্রত্যাশিত হিসাবে প্রত্যাবর্তন করবে

WITH temp(id, geom) AS 
  (VALUES 
      (1, ST_SetSRID(ST_GeomFromText('MultiPoint(12370 361685)'), 31256)),   
      (2, ST_SetSRID(ST_GeomFromText('MultiPoint(13520 360880, 19325 364350)'), 31256)),                                                
      (3, ST_SetSRID(ST_GeomFromText('MultiPoint(11785 367775)'), 31256)),
      (4, ST_SetSRID(ST_GeomFromText('MultiPoint(19525 356305)'), 31256))
),                                              
unions(geoms) AS 
  (SELECT st_buffer(ST_Union(geom), 1000) FROM temp GROUP BY id),
clusters(geoms) AS 
  (SELECT ST_CollectionExtract(unnest(ST_ClusterIntersecting(geoms)), 3) 
     FROM unions),
multis(id, geoms) AS 
  (SELECT row_number() over() as id, geoms FROM clusters)
SELECT id, ST_UNION(d.geom) FROM 
  (SELECT id, (ST_DUMP(geoms)).geom FROM multis) d GROUP BY id;

দুঃখিত, আপনার কাছে ফিরে আসতে এত সময় লেগেছে। কিউজিআইএস-এর বাফার জ্যামিতিগুলি কল্পনা করতে আমার কিছুটা সমস্যা আছে। আমি ব্যবহার আপনার প্রশ্নের সংশোধন করার চেষ্টা করেছি ST_SetSRID, ST_Multiএবং ::geometry(Multipolygon, /*SRID*/), কিন্তু মুহূর্তে এটি কাজ করছে না।
গ্রহিত_বায়ু_মুনুন

ঠিক আছে, আপনি যদি নিজের কোড এবং আরও ভাল কিছু ডেটা পোস্ট করতে পারেন তবে আমি সাহায্য করতে সক্ষম হতে পারি।
জন পাওয়েল

আমি নমুনা পয়েন্ট তৈরি করতে কিছু এসকিউএল যুক্ত করেছি।
গ্রহিত_বায়ু_মুনুন

বিট আজ বেঁধেছে, আমি যত তাড়াতাড়ি সম্ভব ফিরে আসব। কোয়েরিতেও মাল্টিপয়েন্ট কাজ করতে হবে।
জন পাওয়েল

3

এটি করার একটি উপায় হ'ল ST_Unionসমস্ত বাফারকে এক সাথে করা, ST_Dumpফলস্বরূপ বহুভুজের উপাদানগুলি পেতে ফলাফল এবং ST_Intersectsইনপুট পয়েন্টগুলিতে যোগ দিয়ে প্রতিটি ক্লাস্টার কত / কোন পয়েন্ট তৈরি করে তা জানতে।

কল করার আগে পয়েন্টগুলি একসাথে ভাগ করে কোনও যোগদানের প্রয়োজন ছাড়াই এটি করা যায় ST_Buffer। একই দ্রবীভূত বাফারের মধ্যে দুটি পয়েন্ট অবস্থিত হওয়ার জন্য, তাদের চেয়ে কম দূরত্বের পয়েন্টগুলির মধ্যে হપ્સ দ্বারা পৌঁছানো উচিত eps। এটি কেবল সর্বনিম্ন-লিঙ্কেজ ক্লাস্টারিং সমস্যা, যা ব্যবহার করে সমাধান করা যেতে পারে ST_ClusterDBSCAN:

SELECT
  cluster_id,
  ST_Union(ST_Buffer(geom, 1000)) AS geom,
  count(*)                        AS num_points,
  array_agg(point_id)             AS point_ids
FROM (
  SELECT
    point_id,
    ST_ClusterDBSCAN(geom, eps := 2000, minpoints := 1) OVER() AS cluster_id ,
    geom
  FROM points) sq
 GROUP BY cluster_id;

মনে রাখবেন যে এটি বাফার-প্রথম পদ্ধতির মতো হুবহু ফলাফল তৈরি করবে না, কারণ পোস্টজিআইএস বাফারগুলি নিখুঁত চেনাশোনা নয় এবং দুটি পয়েন্ট 1000 মিটার দূরে দুটি 500 মিটার বাফার দ্বারা সংযুক্ত নাও হতে পারে।


আমাদের একই ধারণা ছিল বলে মনে হচ্ছে। আমি আপনার পরীক্ষা করিনি, তবে আমি নিশ্চিত যে এটি কার্যকর এবং আমার চেয়ে আরও পরিষ্কারভাবে than
জন পাওয়েল

দেখে মনে হচ্ছে যে PostGIS 2.2.1 ST_ClusterDBSCAN সমর্থন করে না। আমি পোস্টজিআইএস ২.৩.২ ইনস্টল করেছি, তবে পিজএডমিনে নতুন পোস্টগিজ এক্সটেনশনগুলি এখনও সংস্করণ ২.২.১।
গ্রহিত_বায়ু_মুনুন

0

এই উত্তর অনুসারে আপনি আপনার subquery মধ্যে ST_DUMP করতে চান।

এটার মতো কিছু:

-- collect all buffers to a single multi-polygon feature
-- dissolve overlapping polygon geometries
CREATE TABLE public.pg_multibuffer AS SELECT
    row_number() over() AS gid,
    sub_qry.*
FROM (SELECT
    ST_Dump(ST_Union(ST_Buffer(geom, 1000, 8))::geometry(MultiPolygon, /*SRID*/)) AS geom
FROM
public.multipoints)
AS sub_qry;

এর কারণ হ'ল ST_UNIONসমস্ত বৈশিষ্ট্যগুলির দ্রবীভূত বহুবৃত্তটি ফিরিয়ে দেয় এবং ST_DUMPএটিকে পৃথক বহুভুজ বৈশিষ্ট্যগুলিতে বিভক্ত করে (যা দ্রবীভূত করা হয়েছিল)।


1
এটি আসলে কাজ করবে না, কারণ কাঙ্ক্ষিত বহুগুণ বহুভুজটি ক্লাস্টার করার জন্য যে কোনও বৈশিষ্ট্য হারিয়ে গেছে।
ভিন্স

আমি চেষ্টা করেছি ST_Multi((ST_Dump(ST_Union(ST_Buffer(geom, 1000, 8)))).geom)::geometry(MultiPolygon, /*SRID*/) AS geom, কিন্তু এই পরিবর্তে 4 বৈশিষ্ট্য 3. সৃষ্টি
eclipsed_by_the_moon

ওহ, ঠিক আছে, আপনি সংখ্যা দ্বারা গ্রুপ করতে চান? আপনার GROUP_BYআগে আপনার দরকার হবে ST_UNION
অ্যালেক্স লেথ
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.