পোস্টগিসে অর্কজিআইএস-এর মতো গতি অর্জন করা


62

আমি এখন এক বছরের 3/4 এর জন্য পোস্টগিস ২.০ ব্যবহার করেছি এবং যখন আমি সত্যিই এটি ব্যবহার উপভোগ করছি, অতিরিক্ত জিজ্ঞাসা প্রক্রিয়াকরণের সময়টি এটি আমার ব্যবহারের ক্ষেত্রে মূলত অকেজো হয়ে গেছে।

আমি পৌরসভা ডেটাসেটগুলিতে ভারী জিওপ্রসেসিংয়ের প্রবণতা করি যা প্রায়শই কয়েক লক্ষাধিক মাল্টিপলিজন থাকে। এই বহুগুণগুলি কখনও কখনও খুব অনিয়মিত আকারযুক্ত হয় এবং 4 পয়েন্ট থেকে একাধিক 78,000 পয়েন্টে পরিবর্তিত হতে পারে multip

উদাহরণস্বরূপ, যখন আমি ৫২৫,১৫২ মাল্টিপলিগন সহ একটি পার্সেল ডেটাসেট ছেদ করি যখন 5২৫ মাল্টিপলিগন সমেত একটি জুরি সিকিউরিটি ডেটাসেট রয়েছে, তখন আমি মোট সময় ব্যয় করার জন্য নিম্নলিখিত পরিসংখ্যানগুলি পাই:

ArcGIS 10.0 (on same host with windows 7 OS): 3 minutes
Postgis:56 minutes (not including geometry pre-processing queries)

অন্য কথায়, পোস্টজিইসে আরকজিআইএসের চেয়ে এই ছেদটি করতে 1500% বেশি সময় প্রয়োজন - এবং এটি আমার আরও সহজ প্রশ্নগুলির মধ্যে একটি!

আর্কজিআইএস অনুমিতভাবে দ্রুত সঞ্চালনের অন্যতম কারণ হ'ল আরও ভাল সূচক। কিছু প্রোগ্রামাররা সম্প্রতি এই সূচকগুলি কীভাবে কাজ করে তা নির্ধারণ করেছিল এবং আমি ভাবছি যে কেউ কীভাবে পোস্টগ্রিসে এই সূচীগুলি তৈরি করতে জানেন (বা সারণীগুলি তৈরি করতে হবে যা সূচকে অনুকরণ করবে)। সম্ভবত এটি পোস্টগিসের বেশিরভাগ গতির সমস্যা সমাধান করবে। আমি কেবল আশা করতে পারি যে কোনও উপায় থাকতে হবে, বিশেষত যেহেতু আরকজিআইএস কেবল 4 গিগাবাইট র‍্যাম ব্যবহার করতে পারে যখন আমি আমার পোস্টগ্রিস সার্ভারের চেয়ে 4 গুণ বেশি সময় ব্যবহার করতে পারি!

অবশ্যই পোস্টজিগুলি ধীরে ধীরে চলতে পারে এমন অনেকগুলি কারণ রয়েছে, তাই আমি আমার সিস্টেমের চশমাগুলির একটি বিশদ সংস্করণ সরবরাহ করব:

Machine: Dell XPS 8300 
Processor: i7-2600 CPU @ 3.40 GHz 3.40 GHz 
Memory: Total Memory 16.0 GB (10.0 GB on virtual machine)

Platform: Ubuntu Server 12.04 Virtual Box VM

Potgres Version: 9.1.4
Postgis Version: POSTGIS="2.0.1 r9979" GEOS="3.3.5-CAPI-1.7.5" PROJ="Rel. 4.8.0, 6 March 2012" GDAL="GDAL 1.9.1, released 2012/05/15" LIBXML="2.7.8" LIBJSON="UNKNOWN" TOPOLOGY RASTER

আমি ভিএম নিজেই তৈরি সহ পোস্টগ্রিজ সেটআপ করার জন্য ব্যবহৃত সমস্ত ইনস্টলেশন প্রক্রিয়াটিও বিশদভাবে জানাই

আমি কনফিড ফাইলে ডিফল্ট 24 এমবি থেকে 6 গিগাবাইটে ভাগ করা মেমরিও বাড়িয়েছি এবং পোস্টগ্রাগগুলি চালানোর জন্য নিম্নলিখিত কমান্ডগুলি চালিয়েছি:

sudo sysctl -w kernel.shmmax=7516192768 (I know this setting is deleted every time you restart the OS)
sudo /etc/init.d/postgresql restart

যতদূর আমি এটি বলতে পারি পারফরম্যান্সের দিক থেকে লক্ষণীয় কিছুই নেই।

আমি এই পরীক্ষার জন্য যে ডেটা ব্যবহার করেছি তার লিঙ্কগুলি এখানে:

  1. পার্সেল: tcad_parcels_06142012.shp.zip থেকে অস্টিন, টেক্সাস শহরের
  2. এখতিয়ার: অস্টিনের শহর, টিএক্স থেকে এখতিয়ার সীমানা

ডেটা প্রক্রিয়া করার জন্য আমি যে পদক্ষেপ নিয়েছি তা এখানে:

ArcGIS

  1. আর্কম্যাপে ডেটাসেট যুক্ত করুন
  2. কেন্দ্রীয় টেক্সাস ফুট (সমন্বিত 2277) এ সমন্বিত সিস্টেম সেট করুন
  3. ড্রপডাউন মেনু থেকে ছেদ করার সরঞ্জামটি ব্যবহার করুন

Postgis

পার্সেলগুলি ব্যবহার করে আমদানি করুন:

shp2pgsql -c -s 2277 -D -i -I -W UTF-8 "tcad_parcels_06142012.shp" "public"."tcad_parcels_06142012" |psql -d postgis_testing -U postgres -h local_ip -p 5432

ব্যবহার করে এখতিয়ার আমদানি করুন:

shp2pgsql -c -s 2277 -D -i -I -W UTF-8 "jurisdictions.shp" "public"."jurisdictions" |psql -d postgis_testing -U postgres -h local_ip -p 5432

পার্সেলগুলিতে অবৈধ জ্যামিতি পরিষ্কার করুন:

DROP TABLE IF EXISTS valid_parcels;
CREATE TABLE valid_parcels(
  gid serial PRIMARY KEY,
  orig_gid integer,
  geom geometry(multipolygon,2277)
);
CREATE INDEX ON valid_parcels USING gist (geom);
INSERT INTO valid_parcels(orig_gid,geom)
  SELECT 
    gid 
    orig_gid,
    st_multi(st_makevalid(geom)) 
  FROM 
    tcad_parcels_06142012;
CLUSTER valid_parcels USING valid_parcels_geom_idx;

এখতিয়ারে অবৈধ জ্যামিতি পরিষ্কার করুন:

DROP TABLE IF EXISTS valid_jurisdictions;
CREATE TABLE valid_jurisdictions(
  gid serial PRIMARY KEY,
  orig_gid integer,
  geom geometry(multipolygon,2277)
);
CREATE INDEX ON valid_jurisdictions USING gist (geom);
INSERT INTO valid_jurisdictions(orig_gid,geom)
  SELECT 
    gid 
    orig_gid,
    st_multi(st_makevalid(geom)) 
  FROM 
    jurisdictions;
CLUSTER valid_jurisdictions USING valid_jurisdictions_geom_idx;

ক্লাস্টার চালান:

cluster;

ভ্যাকুয়াম বিশ্লেষণ চালান:

vacuum analyze;

পরিষ্কার টেবিলগুলিতে ছেদটি সম্পাদন করুন:

CREATE TABLE parcel_jurisdictions(
  gid serial primary key,
  parcel_gid integer,
  jurisdiction_gid integer,
  isect_geom geometry(multipolygon,2277)
);
CREATE INDEX ON parcel_jurisdictions using gist (isect_geom);

INSERT INTO parcel_jurisdictions(parcel_gid,jurisdiction_gid,isect_geom)
  SELECT
    a.orig_gid parcel_gid,
    b.orig_gid jurisdiction_gid,
    st_multi(st_intersection(a.geom,b.geom))
  FROM
    valid_parcels a, valid_jurisdictions b
  WHERE
    st_intersects(a.geom,b.geom);

ছেদ কোয়েরি বিশ্লেষণ করুন:

Total runtime: 3446860.731 ms
        Index Cond: (geom && b.geom)
  ->  Index Scan using valid_parcels_geom_idx on valid_parcels a  (cost=0.00..11.66 rows=2 width=1592) (actual time=0.030..4.596 rows=1366 loops=525)
  ->  Seq Scan on valid_jurisdictions b  (cost=0.00..113.25 rows=525 width=22621) (actual time=0.009..0.755 rows=525 loops=1)
Nested Loop  (cost=0.00..61428.74 rows=217501 width=24213) (actual time=2.625..3445946.889 rows=329152 loops=1)
  Join Filter: _st_intersects(a.geom, b.geom)

আমি যা পড়েছি তার থেকে, আমার ছেদটি জিজ্ঞাসাটি দক্ষ এবং পরিষ্কার জ্যামিতিতে 56 মিনিট সময় নেওয়ার জন্য কোয়েরির জন্য আমি কী ভুল করছি তা আমার একেবারেই ধারণা নেই!


2
পোস্টজিআইএস-এ সাধারণ গৌরবময় বিষয় যা গতি বাড়ানোর জন্য একটি বাউন্ডিং বক্স চৌরাস্তা চেক যুক্ত করে। আপনার পুরো ধারাটিতে 'এবং a.geom&&b.geom' যুক্ত করার চেষ্টা করুন এবং দেখুন কতটা তফাত হয়।
শান

2
st_intersects () postgis 2.x এ যে কোনও ছেদকৃত পরীক্ষা করার আগে একটি বাউন্ডিং বক্স কোয়েরি অন্তর্ভুক্ত করে তাই দুর্ভাগ্যক্রমে যে কোনও সময় সাশ্রয় করতে পারে না।
THX1138

1
আপনি কি বিশ্লেষণ বিশ্লেষণ ব্যবহার করে ক্যোয়ারী চালাতে পারেন এবং ফলাফল পোস্ট করতে পারেন
নাথান ডব্লিউ

1
আপনারও সচেতন হওয়া উচিত যে আপনি পোস্টগ্রিস বনাম অর্গগিসে বিভিন্ন ডেটা সেট চালাচ্ছেন যেহেতু আপনি বলেছেন যে আপনি তাদের পোস্ট গ্রাহকে বৈধ করে তোলার জন্য নেক্সট করেছেন।
নিক্লাস আভেন

2
এটি একবার দেখার জন্য কি ডেটা সেটগুলি পাওয়া সম্ভব?
নিক্লাস আভেন

উত্তর:


87

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

INSERT INTO parcel_jurisdictions(parcel_gid,jurisdiction_gid,isect_geom)
SELECT
  a.orig_gid AS parcel_gid,
  b.orig_gid AS jurisdiction_gid,

  st_multi(st_intersection(a.geom,b.geom)) AS geom
FROM
  valid_parcels a, valid_jurisdictions b
WHERE
  st_intersects(a.geom, b.geom) and not st_within(a.geom, b.geom)
UNION ALL
SELECT
  a.orig_gid AS parcel_gid,
  b.orig_gid AS jurisdiction_gid,
  a.geom AS geom
FROM
  valid_parcels a, valid_jurisdictions b
WHERE
  st_within(a.geom, b.geom);

বা এমনকি টর্সার

INSERT INTO parcel_jurisdictions(parcel_gid,jurisdiction_gid,isect_geom)
SELECT
  a.orig_gid AS parcel_gid,
  b.orig_gid AS jurisdiction_gid,
  CASE 
     WHEN ST_Within(a.geom,b.geom) 
     THEN a.geom
     ELSE ST_Multi(ST_Intersection(a.geom,b.geom)) 
  END AS geom
FROM valid_parcels a
JOIN valid_jurisdictions b
ON ST_Intersects(a.geom, b.geom)

আরও দ্রুত ইউএনওএন হতে পারে।


13
ধন্যবাদ আমাকে নেমে গেছে, 3.63 মিনিট! আমি কখনও ভাবিনি যে একটি ইউনিয়ন দ্রুত হবে। এই উত্তরটি আমাকে এখন থেকে প্রশ্নগুলি করার পদ্ধতিতে আমাকে পুনর্বিবেচনা করতে বাধ্য করবে।
THX1138

2
এটি খুব দুর্দান্ত। আমার কর্মক্ষেত্রে একটি কেস হয়েছিল যেখানে আমার স্টি_ইন্টারশেকশন কোয়েরি 30 মিনিট + নিয়েছিল এবং এখন আমি জানি কীভাবে আমি এড়াতে পারি :)
নাথান ডব্লিউ

1
এই প্রশ্ন আমাকে পোস্টগিস শিখিয়েছে! আমি আজ ভাল ঘুমাবো পোস্টগিস কাঁধে কাঁধে কাঁধে রেখে অর্গিসের সাথে :-)
বিনায়ান

2
মার্টিন ডেভিস থেকে আরও একটি বর্ধন, আপনি "ইন বা আউট" ইনলাইন করতে পারবেন? একটি CASE বিবৃতি ব্যবহার করে নির্বাচন করুন এবং ইউনিয়নটিকে সেভাবে এড়িয়ে চলুন question
পল র্যামসে

2
UNIONদুটি ক্যোয়ারী থেকে সদৃশ সারিগুলি সরিয়ে দেয়, তবে এই দুটি ক্যোয়ারির ফলাফল সেটে একই সারিটি থাকতে পারে না। সুতরাং UNION ALL, যা সদৃশ চেক এড়িয়ে চলে, এখানে উপযুক্ত হবে। (আমি UNIONখুব বেশি ব্যবহার করি না , তবে আমি সাধারণত যে সময়গুলি করি তার মধ্যে আমি অনেক বেশি ঘন ঘন ব্যবহার করি UNION ALL))
jpmc26

4

আপনি যদি "st_multi(st_intersection(a.geom,b.geom))"অংশটি বাদ দেন তবে কি হবে ?

নীচের কোয়েরিটি কি এটি ছাড়া একই জিনিসটির অর্থ নয়? আপনার সরবরাহ করা ডেটাতে আমি এটি চালিয়েছি।

INSERT INTO parcel_jurisdictions(parcel_gid,jurisdiction_gid,isect_geom)
  SELECT
    a.orig_gid parcel_gid,
    b.orig_gid jurisdiction_gid,
    a.geom
  FROM
    valid_parcels a, valid_jurisdictions b
  WHERE
    st_intersects(a.geom,b.geom);

কনফিগারেশন

Processor: AMD Athlon II X4 635 2.9 GHz 
Memory: 4 GB
Platform: Windows 7 Professional
Potgres Version: 8.4
Postgis Version: "POSTGIS="2.0.1 r9979" GEOS="3.3.5-CAPI-1.7.5" PROJ="Rel. 4.8.0, 6 March 2012" GDAL="GDAL 1.9.1, released 2012/05/15" LIBXML="2.7.8" LIBJSON="UNKNOWN" TOPOLOGY RASTER"

ফলাফল বিশ্লেষণ করুন

"Nested Loop  (cost=0.00..7505.18 rows=217489 width=1580) (actual time=1.994..248405.616 rows=329150 loops=1)"
"  Join Filter: _st_intersects(a.geom, b.geom)"
"  ->  Seq Scan on valid_jurisdictions b  (cost=0.00..37.25 rows=525 width=22621) (actual time=0.054..1.732 rows=525 loops=1)"
"  ->  Index Scan using valid_parcels_index on valid_parcels a  (cost=0.00..11.63 rows=2 width=1576) (actual time=0.068..6.423 rows=1366 loops=525)"
"        Index Cond: (a.geom && b.geom)"
"Total runtime: 280087.497 ms"

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