根据经纬度坐标查询最近的门店
1. 直接通过 mysql 查询
DB::table('shop')->selectRaw("id,lon,lat,
ROUND(ST_DISTANCE(point(lon,lat),point({$lon},{$lat})) /0.0111,2) distance")
->orderBy('distance')
->first();
2. 查询所有坐标,循环计算距离
/** 获取用户最近的店铺
* @param $shopList
* @param $lon
* @param $lat
* @return array
*/
function nearestShop($shopList, $lon, $lat){
$arr = [];
foreach ($shopList as $key => $shop){
$arr[$key] = getDistance($lon, $lat, $shop->lon, $shop->lat);
}
asort($arr); //按距离排序
return $shopList[array_keys($arr)[0]];
}
/** 根据坐标计算距离
* @param float $lon1
* @param float $lat1
* @param float $lon2
* @param float $lat2
* @param int $unit 单位 2是公里
* @param int $decimal 四舍五入小数点后位数
* @return float
*/
function getDistance($lon1, $lat1, $lon2, $lat2, $unit = 2, $decimal = 2){
$EARTH_RADIUS = 6371; // 地球半径系数
//将角度转为狐度
$radLng1 = deg2rad($lon1);
$radLat2 = deg2rad($lat2);
$radLat1 = deg2rad($lat1);
$radLng2 = deg2rad($lon2);
$distance = 2 * asin(sqrt(pow(sin(($radLat1-$radLat2) / 2), 2) + cos($radLat1) * cos($radLat2) * pow(sin(($radLng1-$radLng2) / 2), 2))) * $EARTH_RADIUS * 1000;
if ($unit === 2) {
$distance /= 1000;
}
return round($distance, $decimal);
}
本作品采用《CC 协议》,转载必须注明作者和本文链接
推荐文章: