【问题标题】:Zipcodes & Distance邮政编码和距离
【发布时间】:2011-04-01 02:14:33
【问题描述】:

我有一个 MySQL 数据库中的邮政编码列表及其纬度和经度数据(列名:ZipCode、Lat、Lon)。

现在我必须发出搜索请求(搜索邮政编码)以从网站中提取信息。当我提出这个搜索请求时,结果包括邮政编码半径 50 公里范围内的所有信息。

现在,我不想发出不必要的大量搜索请求,所以我想尽量减少邮政编码的数量。所以我正在寻找一种过滤所有邮政编码的方法,这样我就只有它们之间的距离大于 50 公里的邮政编码。

不幸的是,我不知道该怎么做。 有人可以帮我解决这个问题吗?

【问题讨论】:

  • 将“它们之间>50km”更改为“它们之间
  • @Chris 我认为 >50km 是故意的。我们想要一组 50 公里半径的搜索,以尽可能少的搜索覆盖所有邮政编码。因此,我们可以丢弃与我们已经选择的邮政编码相距 50 公里以内的任何邮政编码,而我们保留的邮政编码将相距 >50 公里。
  • 结果应该是两个邮政编码之间的距离大于 50 公里的邮政编码列表。一开始我有一个列表,例如10.000 个邮政编码,其中包含大量邮政编码,但距离非常小。之后我应该有一个较小的邮政编码列表(例如 2000 个邮政编码),它们之间的距离 > 50 公里。
  • 您可以尝试问gis.stackexchange.com 的这个问题,这是一个类似 stackoverflow 的新网站,用于解决地理信息系统 (GIS) 问题

标签: mysql geolocation distance latitude-longitude


【解决方案1】:

我遇到了类似的问题,我使用此解决方案找到了答案。不确定您使用的是 java 还是其他语言,但该逻辑可用于任何编程语言 Geo Location API and finding user within a radius

【讨论】:

    【解决方案2】:

    您可能有兴趣查看以下演示文稿:

    作者描述了如何在 MySQL 中使用 Haversine Formula 将搜索限制在定义的范围内。他还介绍了如何使用 latitude 和 longitude 列上的传统索引来避免对此类查询进行全表扫描。

    【讨论】:

      【解决方案3】:

      这个问题之前已经在here on SO 讨论过各种解决方案

      【讨论】:

        【解决方案4】:

        Daniel 的链接涉及选择给定纬度/经度 50 公里内的所有邮政编码。一旦你能做到这一点,你就可以像这样构建一个经过过滤的邮政编码列表......

        1. 随机选择一个邮政编码并将其添加到过滤列表中
        2. 删除所选邮政编码 50 公里范围内的所有邮政编码
        3. 从剩余的邮政编码中随机选择一个新的邮政编码,重复直到没有剩余。

        您知道您只选择距离已选择的邮政编码超过 50 公里的邮政编码,并且您知道一旦原始表格是空的,它一定是空的,因为所有邮政编码都位于您选择的至少一个 50 公里范围内邮政编码。

        这并不能保证最小的邮政编码列表,结果的大小将取决于随机选择。但是,我认为这个简单的算法可能已经“足够好”了,节省一些搜索并不能证明为找到真正的最佳解决方案而付出的额外努力是合理的。

        【讨论】:

          【解决方案5】:

          好吧,我认为没有其他方法可以迭代每个请求的所有行并通过计算所选邮政编码与其他邮政编码(所有这些邮政编码)之间的距离来过滤它们,基于纬度和经度。

          我正在使用类似的东西... http://webarto.com/googlemaps http://webarto.com/izrada-web-stranica/belgrade

          两个LL之间距离的PHP函数...

          function distance($lat1, $lon1, $lat2, $lon2){ 
            $theta = $lon1 - $lon2; 
            $dist = sin(deg2rad($lat1)) * sin(deg2rad($lat2)) +  cos(deg2rad($lat1)) * cos(deg2rad($lat2)) * cos(deg2rad($theta)); 
            $dist = acos($dist); 
            $dist = rad2deg($dist); 
            $miles = $dist * 60 * 1.1515;
            return round($miles * 1.609344,3);
          }
          

          我是这样计算的……

          $sql = mysql_query("SELECT * FROM geoip WHERE city = '$city'");
          while($row = mysql_fetch_array($sql)){
              $ll = explode(",",$row["ll"]);
              $x = distance(44.5428009033,18.6693992615,$ll[0],$ll[1]);
              $road = intval($x+($x/3));
          
              echo "Distance between ".$row["city"]." and Tuzla is ".$x." kilometers of airline, that's about ".$road." kilometers of road way.";
          }
          

          【讨论】:

            【解决方案6】:

            您可以使用 google geocoding api ,它允许您获取 2 个位置之间的距离(纬度/经度,它还允许您从纬度/经度获取 zip)。从中您应该能够获取每个邮政编码之间的距离并将它们放入表格中,然后您可以仅对这些进行搜索。

            【讨论】:

            • 如何在表格中存储邮政编码之间的距离?这个距离是多少?您是说有一个距离表,其中包含 id、id(zipcode1)、id(zipcode2)、距离,并且对于 2 个邮政编码的每个组合都有一个条目?
            • 不,我会有一个多对多,将 zip 与 50 英里内的其他 zip 相关联,或者如果您更喜欢不太标准化的方法,您可以使用 zipcode1,第二列是逗号列表在 50 英里范围内的拉链中,如果性能为王,这将起作用。你只需要
            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多