PostGIS: सिंगल साइड ST_Buffer ऑफ लाइनरिंग अजीब आउटपुट उत्पन्न करता है

Aug 18 2020

नीचे दिए गए उदाहरण में मेरे पास एक linestring PostGIS टेबल (काले और पीले रंग में) और एक तरफा ST_Buffer आउटपुट बहुभुज (लाल रंग में) है। बफर दूरी linestring तालिका में संग्रहीत विशेषता मान पर आधारित है।

जैसा कि आप देख सकते हैं कि बफ़र्स में से एक गलत है, और इसमें से एक निश्चित राशि के लिए स्वयं का एक भाग काट देता है। ऐसा क्यों हुआ है? क्या इसे ठीक किया जा सकता है? ऐसा मुद्दा लगता है जहाँ अलंकार धारा अवतल हो जाती है।

एक समान क्वेरी का उपयोग करके अपने लिए यह प्रयास करें:

SELECT ST_BUFFER('LineString (638327 331059, 638337 331048, 638337 331037, 638343 331023, 638358 331014, 638380 330991, 638382 330978, 638391 330966, 638410 330959, 638420 330953)',50,'side=right')

एक अन्य उदाहरण में मैं यह देख रहा हूं (काली रेखा 1 विशेषता है, जैसा कि बफर बहुभुज है):

और इस के साथ एक कोशिश:

SELECT ST_BUFFER('LineString (600296 172961, 600304 172962, 600307 172965, 600307 172969, 600307 172971, 600309 172974, 600308 172976, 600307 172979, 600306 172981, 600307 172982, 600311 172980, 600313 172979, 600317 172979, 600321 172982, 600325 172982, 600327 172979, 600328 172976, 600331 172974, 600338 172974)',10,'side=right')

अजनबी परिणामों के लिए बफर दूरी बढ़ाएँ। ईपीएसजी: दोनों मामलों में 27700।

जवाब

7 dr_jts Aug 18 2020 at 05:53

ये एकल-पक्षीय बफर एल्गोरिथ्म में कमियों के कारण होते हैं (बग नहीं, वे एल्गोरिदम डिजाइन की ज्ञात सीमाएं हैं)।

इसे GEOS समस्या के रूप में लॉग किया गया है । हालांकि अभी तक कोई ईटीए फिक्स नहीं है।

TheoF Aug 20 2020 at 01:04

मैंने एक वर्कअराउंड पाइपलाइन बनाई है जो इस समस्या को ठीक करती है। इसमें रास्ते में कुछ अस्थायी मध्यवर्ती तालिकाओं को बनाना शामिल है, लेकिन आप उन्हें मक्खी पर हटा सकते हैं।

  1. अपनी लाइन को ST_BUFFERसामान्य रूप से उपयोग करते हुए बफ़र करें , आपके पास अराजक आउटपुट नहीं होगा (यानी। 'side=left/right'पैरामीटर का उपयोग न करें )।
  2. का प्रयोग करें ST_Splitकेंद्र लाइन का उपयोग कर के साथ आधे में चरण 1 से बफर विभाजित करने के लिए। ST_UNIONआसन्न कनेक्टिंग लाइनों के साथ लाइन! यह सुनिश्चित करेगा कि काटने की रेखा बफर के माध्यम से और उसके बाहर फैले । यह अन्यथा कुछ भी नहीं कटेगा।
  3. अपनी लाइन को फिर से बफर करें लेकिन इस बार केवल एक तरफ बफर करें। यह वह पक्ष होना चाहिए जिसे आप नहीं चाहते हैं।
  4. ST_PointOnSurfaceप्रत्येक 'गलत' साइड बफर आकार के लिए एक पॉइंट टेबल बनाएं ।
  5. विभाजित बिंदुओं को भेदते हुए पाए गए बहुभुज बफर (चरण 2 से) से किसी भी बहुभुज को हटाने के लिए इस नए बिंदु तालिका का उपयोग करें।
  6. अब आपको पूर्ण बफ़र आकृति के साथ छोड़ दिया गया है जिसमें से 'गलत' पक्ष हटा दिया गया है। अर्थात। आपको वांछित सही पक्ष के साथ छोड़ दिया गया है।

मैंने इसे बड़े पैमाने पर अभिव्यक्त किया है और प्रत्येक पंक्ति खंड के लिए मान लिया है कि आपके पास काटने के साथ मदद करने के लिए एक निकटवर्ती कनेक्टिंग लाइन है। मैंने यह एक सेगमेंट के लिए भी किया है जिसमें कई सेगमेंट हैं। इसलिए मैंने उपरोक्त चरणों के प्रत्येक पुनरावृत्ति को सम्मिलित करने के लिए एक होस्ट तालिका का उपयोग किया। प्रत्येक लाइन सेगमेंट के माध्यम से लूप करने के लिए मैंने सुनिश्चित किया कि लाइन टेबल में एक ऑटो-इन्क्रिमेंटिंग आईडी कॉलम था (इसलिए प्रत्येक लाइन सेगमेंट के लिए मैं इसे सेगमेंट से पहले और उसके बाद मर्ज कर सकता था: अर्थात। n-1, n, n + 1)। अधिक स्पष्ट करने के लिए मैं जल्द ही इस उत्तर को अपडेट करूंगा।