Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/229.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
基于最小和最大半径的PHP距离_Php_Mysql_Pdo_Distance - Fatal编程技术网

基于最小和最大半径的PHP距离

基于最小和最大半径的PHP距离,php,mysql,pdo,distance,Php,Mysql,Pdo,Distance,首先,我知道有关于这个函数的问题的答案,我浏览了其中的大部分,我可以找到我想要的答案。我想做的事情可以很简单地用一幅图片来解释: 现在,让我们为这幅图像添加一些叙述。我想做的是,在MySQL中,计算从机场到数据库中所有机场的距离,如果它们位于半径A和半径B之间,则将它们添加到我的数组中,以便以后处理 function distance($lat1, $lon1, $lat2, $lon2, $unit) { $theta = $lon1 - $lon2; $dist = sin(deg

首先,我知道有关于这个函数的问题的答案,我浏览了其中的大部分,我可以找到我想要的答案。我想做的事情可以很简单地用一幅图片来解释:

现在,让我们为这幅图像添加一些叙述。我想做的是,在MySQL中,计算从机场到数据库中所有机场的距离,如果它们位于半径A和半径B之间,则将它们添加到我的数组中,以便以后处理

function distance($lat1, $lon1, $lat2, $lon2, $unit) {
  $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;
  $unit = strtoupper($unit);

  if ($unit == "K") {
    return ($miles * 1.609344);
  } else if ($unit == "N") {
     return ($miles * 0.8684);
    } else {
        return $miles;
        }
}
这是我目前用来计算的,但它是用php编写的,速度非常慢。我希望升级代码,以便mysql服务器进行计算。我也在尝试用PHP PDO来完成这一切。如果有人能帮助我,我们将不胜感激。

选项1: 通过切换到支持GeoIP的数据库或使用MySQLs基本GeoIP功能,在数据库上进行计算

备选案文2: 在数据库上进行计算:您使用的是MySQL,因此下面的存储过程应该会有所帮助

CREATE FUNCTION distance (latA double, lonA double, latB double, LonB double)
    RETURNS double DETERMINISTIC
BEGIN
    SET @RlatA = radians(latA);
    SET @RlonA = radians(lonA);
    SET @RlatB = radians(latB);
    SET @RlonB = radians(LonB);
    SET @deltaLat = @RlatA - @RlatB;
    SET @deltaLon = @RlonA - @RlonB;
    SET @d = SIN(@deltaLat/2) * SIN(@deltaLat/2) +
    COS(@RlatA) * COS(@RlatB) * SIN(@deltaLon/2)*SIN(@deltaLon/2);
    RETURN 2 * ASIN(SQRT(@d)) * 6371.01;
END//
如果数据库中有纬度和经度索引,则可以通过在PHP中计算初始边界框($minLat、$maxLat、$minLong和$maxLong),并基于此将行限制为条目的子集,从而减少需要计算的计算数量(其中纬度在$minLat和$maxLat之间,经度在$minLong和$maxLong之间)。然后MySQL只需要对该行子集执行距离计算

如果您只是使用skv提供的SQL语句(或计算距离的存储过程),那么SQL仍然必须查看数据库中的每个记录,并计算数据库中每个记录的距离,然后才能决定是返回该行还是放弃该行

由于计算的执行速度相对较慢,因此最好减少需要计算的行集,消除明显超出所需距离的行,这样我们只对较少的行执行昂贵的计算

考虑到你所做的基本上是在地图上画一个圆,以你的初始点为中心,以距离为半径;然后公式简单地确定哪些行在该圆内……但它仍然需要检查每一行

使用边界框就像先在地图上画一个正方形,其左、右、上、下边缘与中心点保持适当的距离。然后将在该框内绘制圆,圆上最北、最东、最南和最西的点接触框的边界。一些行将落在该框外x、 因此SQL甚至不用费心去计算那些行的距离,它只计算那些落在边界框内的行的距离,看看它们是否也落在圆内

在PHP中,我们可以使用一个非常简单的计算,根据我们的距离计算出最小和最大纬度和经度,然后在SQL语句的WHERE子句中设置这些值。这实际上是我们的框,超出该框的任何内容都会自动丢弃,而无需实际计算其距离


对此有很好的解释(使用PHP代码)对于任何打算用PHP做地理定位工作的人来说,这应该是一本必备的读物。

你可以在机场周围使用六边形网格和螺旋搜索。下面是一个相邻平铺的示例:

只需复制代码,高亮显示,然后点击“代码”按钮-它将所有内容缩进四个空格,这是co的标记格式你看了我对这个问题的回答了吗?我使用了四键。是的,但这对我正在尝试的工作来说太复杂了。这是一个简单的应用程序。关于复杂数学的所有这些都是不必要的。更不用说这有点超出我的理解,我不想使用任何我自己不100%理解的东西。我重写我的代码并大大加快了速度。这不是我想要的,但正如我所说的,它的速度要快得多,暂时可以满足应用程序的需要。感谢你在这方面帮助过我的所有人。好的,我想澄清一下,这将允许我计算最小值内点之间的距离d用户提供的最大距离?您需要做一些工作:使用基于外圆的边界框,并在SQL的WHERE子句中进行设置,在SQL查询选择列表中计算该结果子集的距离,然后使用HAVING子句测试计算的距离是否在内圆半径a之间外圆半径