मैं दूरी और अक्षांश / देशांतर के लिए बाउंडिंग बॉक्स की गणना कैसे करूं


13

मुझे किसी दिए गए WGS84 अक्षांश और WGS84 देशांतर और दूरी के लिए एक बाउंडिंग बॉक्स या सर्कल की गणना करने में सक्षम होने की आवश्यकता है, लेकिन पता नहीं है कि कहां से शुरू करें!

स्टार्ट लेट / लोन से दूरी 10Km या उससे कम होगी।

क्या किसी के लिए यह संभव होगा कि वह मुझे कुछ संकेत / उदाहरण दे


उन हलकों के लिए जो पोल पर या तो कवर नहीं करते हैं, gis.stackexchange.com/questions/19221 ... पर एक विस्तृत उत्तर दिया गया है । लेकिन यह पूरी कहानी नहीं है, जैसा कि वर्तमान उत्तरों का सुझाव है: आप गति-सटीकता-प्रोग्राम जटिलता ट्रेडऑफ़ बना सकते हैं। ध्यान दें, यह भी है कि जब आप लेट-लोन में काम करते हैं (कठिनाइयों -1 -180 डिग्री मेरिडियन में) को निर्दिष्ट करने में "रैप-अराउंड" समस्या होती है। इसके समाधान के लिए, gis.stackexchange.com/questions/17788/… देखें ।
whuber

क्या आपको वास्तव में एक बॉक्स की आवश्यकता है, या किसी दिए गए बिंदु के पास 4 अंक पर्याप्त होंगे? एक बिंदु p को देखते हुए, p से दिशा NE, SW, SE और NW पर 4 अंक d दूरी ज्ञात करें।
Kirk Kendkendall

@ किर्क - अगर आपके पास 4 बिंदुओं का निर्देशांक है, तो आपके पास बॉक्स है ...
martinstoeckli

@martinstoeckli ठीक है, मैं सिर्फ एक बॉक्स पर एक बॉक्स की तरह लग रहा है क्या कल्पना करने के लिए नहीं होने से समस्या को आसान बनाने की उम्मीद कर रहा था। ध्यान दें कि समस्या को सामान्य किया जा सकता है ताकि यह स्पष्ट हो सके कि बॉक्स के किनारों को एक ही अक्षांश / देशांतर (दूसरे शब्दों में एक घुमाया हुआ बॉक्स) पर गिरने की आवश्यकता नहीं है।
कर्क कुक्केंडल

@ किर्क - आह ठीक है, अगर आपको इसकी आवश्यकता है कि वास्तव में, तो आप बिल्कुल सही हैं। मुझे लगता है कि संभव उम्मीदवारों को जल्दी से खोजने के लिए बॉक्स केवल उपयोगी है। यह जांचने के लिए कि क्या दो बिंदु एक निश्चित दूरी (सर्कल) के भीतर हैं, अधिक जटिल हैवरसिन सूत्र का उपयोग किया जा सकता है।
मार्टस्टोएक्ली

जवाबों:


15

डब्ल्यूजीएस-क्या? डब्ल्यूजीएस -84? आपको किस सटीकता की आवश्यकता है, इसके आधार पर, आपको बहुत अधिक जानकारी जानने की आवश्यकता हो सकती है - मेरा अनुमान है कि आपने मतदान क्यों किया है, हालांकि किसी ने यह कहते हुए टिप्पणी छोड़ने की जहमत नहीं उठाई।

यहाँ दो तरीके हैं:

गलत, लेकिन शायद 'काफी अच्छा'

अक्षांश की एक डिग्री WGS-84 डेटम का उपयोग करके लगभग 10001.965729 / 90 किलोमीटर (भूमध्य रेखा से ध्रुव की दूरी, नब्बे डिग्री से विभाजित) या 111.113 किलोमीटर है। यह पृथ्वी के आकार के कारण एक सन्निकटन है, और क्योंकि दूरियां बदल जाती हैं जैसा कि आप ध्रुवों से संपर्क करते हैं (अक्षांश का उपयोग करने का एक कारण, देशांतर नहीं - अंततः देशांतर की एक डिग्री की दूरी शून्य है!) पृथ्वी भी एक आदर्श नहीं है। क्षेत्र। ये दोनों मेरे दूसरे उत्तर में एक अधिक जटिल प्रक्षेपण- और डेटा-आधारित दृष्टिकोण का उपयोग करने के कारण हैं।

10001.965729km = 90 degrees
1km = 90/10001.965729 degrees = 0.0089982311916 degrees
10km = 0.089982311915998 degrees

यह दशमलव डिग्री का उपयोग कर रहा है, डिग्री / मिनट / सेकंड का नहीं।

तो, आपका बाउंडिंग बॉक्स आपकी बात, प्लस और माइनस 0.08999 डिग्री होगा। वैकल्पिक रूप से आप इस संख्या को त्रिज्या के रूप में उपयोग कर सकते हैं, जिससे आपको एक बाउंडिंग सर्कल मिल सकता है

इसे पढ़ने वाला कोई भी जीआईएस व्यक्ति थरथराएगा। यह ज्यादातर सटीक होगा, हालांकि, आप दुनिया में कहां हैं इसके आधार पर। 10 किमी के दायरे के लिए यह ठीक होना चाहिए।

बहुत अधिक सटीक, लेकिन अधिक कोड

एक प्रक्षेपण पुस्तकालय का उपयोग करें और अपने डेटा को निर्दिष्ट करें, आदि। मैं प्रोज 4 की सलाह देता हूं; इसका व्यापक रूप से उपयोग किया जाता है इसलिए Google इसके बारे में प्रश्नों के लिए परिणाम की ढेरियां देता है, और डेल्फी रैपर हैं । यदि आपको इसका उपयोग करने में समस्या है, तो SO पर यहां एक और प्रश्न पोस्ट करें - यह इस दायरे से बाहर है। प्रोज 4 वेबसाइट में मूल एपीआई का उपयोग करने वाले उदाहरण हैं, और हालांकि ये सी में हैं यह काफी आसानी से अनुवाद योग्य होना चाहिए। उनका एपीआई संदर्भ शुरू करने के लिए सबसे अच्छी जगह है, इसके बाद अक्सर पूछे जाने वाले प्रश्न

मैं WGS-84 को एक बुनियादी डेटम (पृथ्वी का प्रतिनिधित्व) के रूप में उपयोग करूंगा, जब तक कि आप एक विशिष्ट को नहीं जानते जिसे आप उपयोग करना चाहते हैं, या जो आपके निर्देशांक बनाने के लिए उपयोग किया गया था। यह आमतौर पर प्रयोग किया जाता है और बहुत सटीक है।

यदि आपकी स्थिति Google मानचित्र (उदाहरण के लिए) से आती है, तो एक Mercator प्रक्षेपण निर्दिष्ट करें। आप एक और प्रक्षेपण, या यूटीएम निर्देशांक का उपयोग करना चाहते हैं, कह सकते हैंअक्षांश और देशांतर के बजाय, आपके डेटा के स्रोत पर निर्भर करता है और यदि आप एक छोटे से स्थानीय क्षेत्र के लिए उच्च सटीकता चाहते हैं। (UTM के कई जोन हैं, जिनमें से सभी विरूपण को बदल देते हैं ताकि उस क्षेत्र के भीतर, यह अत्यधिक सटीक हो; यदि आप इसके बाहर निर्देशांक के लिए एक ज़ोन का उपयोग करते हैं, तो इससे विकृति बहुत बढ़ जाएगी जैसे ही आप दूर जाते हैं। यदि आप संपूर्ण पृथ्वी को एक से अनुमानित करते हैं। ज़ोन, यह अपरिचित हो सकता है। लेकिन एक ज़ोन के भीतर, UTM अनुवाद आपके बारे में जितना हो सके उतना अच्छा होगा। निर्देश आमतौर पर मीटर में निर्दिष्ट होते हैं, डिग्री में नहीं, इसलिए यह आपके लिए अधिक उपयोगी हो सकता है, आपको 10 किमी की आवश्यकता है। त्रिज्या। 10 किमी एक क्षेत्र के भीतर आसानी से है, आपको बस अपने केंद्र के आधार पर उपयुक्त क्षेत्र का चयन करने की आवश्यकता है। केवल मुश्किल बिट है जब आप एक सीमा पर पहुंचते हैं: यह एक सामान्य स्थिति है, और यह ठीक है, बस होआप जो चुनते हैं, उसके अनुरूप । Proj4 आपको अनुमानों का अनुवाद करने देगा, इसलिए आप अपने मर्केटर WGS-84 lat / long से UTM ज़ोन n तक जा सकते हैं , उदाहरण के लिए, या दो UTM ज़ोन से।)


2
जहां हम रहते हैं, एक सर्वेक्षणकर्ता ने एक बार मुझे बताया था कि वह अपनी मानसिक गणनाओं के लिए 1 डिग्री का उपयोग लगभग 108 किमी के बराबर करता है। मानसिक रूप से 10 किमी लगभग 0.1 डिग्री है। जैसा कि ये 0.089982311915998 के बजाय 1 महत्वपूर्ण अंक (2 या 3 सबसे अधिक) के सटीक होने का अनुमान लगाने के लिए सबसे अच्छा अनुमान है, क्योंकि इसका मतलब सटीक स्तर है।
स्टीफन क्वान

1
अक्षांशों को ध्यान में रखते हुए, डिग्री को अधिक सटीक गणना करना वास्तव में मुश्किल नहीं है। चूंकि कंप्यूटर गणना करता है, एक अनुमान के साथ कुछ भी प्राप्त नहीं हुआ है (मेरे उदाहरण में पहला फ़ंक्शन देखें)।
martinstoeckli

3

मान लें कि आप किसी डेटाबेस में एक क्वेरी बनाना चाहते हैं, तो आप संभवतः एक तेज़ (गलत) खोज करना चाहते हैं, और बाद में परिणामी स्थानों के लिए दूरी की गणना करना चाहते हैं। क्या आपका परिदृश्य यही है?

निम्न कार्य (PHP में, क्षमा करें) अक्षांश और देशांतर में अंतर की गणना करेगा। यह अंतर आपके खोज बिंदु के अक्षांश पर निर्भर करता है। डेटाबेस में तेजी से खोज करने के लिए उनका उपयोग करें (एक छोटी सहिष्णुता के साथ)। बॉक्स की गणना केवल अक्षांश + -DeltaLatitude और देशांतर + -deltaLongitude के साथ की जा सकती है।

deltaLatitude[rad] = distance[m] / earthRadius[m]
deltaLongitude[rad] = distance[m] / (cos(latitude[rad]) * $earthRadius[m])

/**
 * Calculates the deltas in latitude and longitude to use, for a db search
 * around a location in the database.
 * @param float $distance Radius to use for the search [m]
 * @param float $latitude Latitude of the location, we need the angle deltas for [deg decimal]
 * @param float $deltaLatitude Calculated delta in latitude [deg]
 * @param float $deltaLongitude Calculated delta in longitude [deg]
 * @param float $earthRadius Mean earth radius in [m]
 */
public static function angleFromSphericDistance($distance, $latitude,
  &$deltaLatitude, &$deltaLongitude, $earthRadius = 6371000)
{
  $lat = deg2rad($latitude);

  $radiusOnLatitude = cos($lat) * $earthRadius;
  $deltaLatitude = $distance / $earthRadius;
  $deltaLongitude = $distance / $radiusOnLatitude;

  $deltaLatitude = rad2deg($deltaLatitude);
  $deltaLongitude = rad2deg($deltaLongitude);
}

साथ haversine सूत्र , आप क्षेत्र पर दूरी की गणना कर सकते हैं। पाया स्थानों में से प्रत्येक के लिए इसका उपयोग करें, "सटीक" दूरी प्राप्त करने के लिए। इस तरह से आप परीक्षण कर सकते हैं, अगर दो स्थान एक निश्चित दायरे (बॉक्स के बजाय एक चक्र) के भीतर हैं।

/**
 * Calculates the great-circle distance between two points, with
 * the Haversine formula.
 * @param float $latitudeFrom Latitude of start point in [deg decimal]
 * @param float $longitudeFrom Longitude of start point in [deg decimal]
 * @param float $latitudeTo Latitude of target point in [deg decimal]
 * @param float $longitudeTo Longitude of target point in [deg decimal]
 * @param float $earthRadius Mean earth radius in [m]
 * @return float Distance between points in [m] (same as earthRadius)
 */
public static function haversineGreatCircleDistance(
  $latitudeFrom, $longitudeFrom, $latitudeTo, $longitudeTo, $earthRadius = 6371000)
{
  // convert from degrees to radians
  $latFrom = deg2rad($latitudeFrom);
  $lonFrom = deg2rad($longitudeFrom);
  $latTo = deg2rad($latitudeTo);
  $lonTo = deg2rad($longitudeTo);

  $latDelta = $latTo - $latFrom;
  $lonDelta = $lonTo - $lonFrom;

  $angle = 2 * asin(sqrt(pow(sin($latDelta / 2), 2) +
    cos($latFrom) * cos($latTo) * pow(sin($lonDelta / 2), 2)));
  return $angle * $earthRadius;
}

3

यह जांचने के लिए कि एक अक्षांश / लोन एक बाउंडिंग सर्कल के भीतर या बाहर है, आपको अपने संदर्भ लेट / लोन से उस लेट / लोन पॉइंट की दूरी की गणना करने की आवश्यकता है जिसे आप परीक्षण करना चाहते हैं। चूँकि आपकी दूरी 10 किमी या उससे कम है, इसलिए मैं सादगी के कारण हवेर्सिन के बजाय दूरी को प्राप्त करने के लिए इक्व्रीनिएरंग इम्प्लांटेशन का उपयोग करने की कोशिश करूंगा। किमी में दूरी पाने के लिए:

x = (lonRef - lon) * cos ( latRef )
y = latRef - lat
distance = EarthRadius * sqrt( x*x + y*y )

महत्वपूर्ण नोट: इन फॉर्मूला में लैट / लोन रेडियन में हैं डिग्री नहीं। EarthRadius का विशिष्ट मूल्य 6371 किमी है जो किमी की इकाइयों में दूरी लौटाएगा। अब यह एक सरल परीक्षा है यदि आपकी दूरी सर्कल के भीतर या बाहर है। यदि एक बाउंडिंग सर्कल काम करता है, तो मैं उसके साथ जाऊंगा।

एक बाउंडिंग आयत के लिए, मुझे लगता है कि आप आयत को भूमध्य रेखा के समानांतर होने से परिभाषित करना चाहते हैं। मैं तब सीमा / असर गणनाओं का उपयोग करके बाउंडिंग बॉक्स के कोनों की गणना करता हूं (बीयरिंग 45 डिग्री, 135 डिग्री, 225 डिग्री और 315 डिग्री हो)। वहां से, मैं मान लूंगा कि आप ध्रुवों के आसपास नहीं हैं और बहुभुज परीक्षण में एक बिंदु का उपयोग करते हैं।


2

नीचे T-SQL कोड है जिसे मैं SQL-Server 2012 में बाउंडिंग बॉक्स के निर्माण के लिए उपयोग करता हूं। मेरे मामले में मुझे Lat, Long के लिए दशमलव मान मिलते हैं। मैं SQL STDistanceफ़ंक्शन का उपयोग करने से पहले पंक्तियों की संख्या को जल्दी से सीमित करने के लिए इसका उपयोग करता हूं ताकि यह सत्यापित किया जा सके कि परिणाम वास्तव में विशेष दूरी के भीतर हैं। भूगोल फ़ंक्शन SQL सर्वर में बहुत महंगे हैं, इस प्रकार बाउंडिंग बॉक्स का निर्माण करके मैं इसे निष्पादित करने की संख्या को बहुत कम करने में सक्षम हूं।

DECLARE @Lat DECIMAL(20, 13) = 35.7862
   ,@Long DECIMAL(20, 13) = -80.3095
   ,@Radius DECIMAL(7, 2) = 5
   ,@Distance DECIMAL(10, 2)
   ,@Earth_Radius INT = 6371000;

SET @Distance = @Radius * 1609.344;

DECLARE @NorthLat DECIMAL(20, 13) = @Lat + DEGREES(@distance / @Earth_Radius)
   ,@SouthLat DECIMAL(20, 13) = @Lat - DEGREES(@distance / @Earth_Radius)
   ,@EastLong DECIMAL(20, 13) = @Long + DEGREES(@distance / @Earth_Radius / COS(RADIANS(@Lat)))
   ,@WestLong DECIMAL(20, 13) = @Long - DEGREES(@distance / @Earth_Radius / COS(RADIANS(@Lat)));

SELECT *
    FROM CustomerPosition AS cp
    WHERE (
            cp.Lat >= @SouthLat
            AND cp.Lat <= @NorthLat )
        AND (
              cp.Long >= @WestLong
              AND cp.Long <= @EastLong )
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.