JS计算两个地理坐标点之间的距离(支持米与公里/千米)

一、 前言

  1. 角度转弧度:将经纬度从角度转换为弧度

  2. 计算差值:计算两点间的纬度和经度差

  3. 应用哈弗辛公式

    • sin²(Δlat/2) + cos(lat1) * cos(lat2) * sin²(Δlng/2)
    • 计算两点间的中心角
  4. 计算弧长2 * R * arcsin(√上述结果)

  5. 单位转换:根据参数返回公里或米单位

二、 代码注释及参数详解

注意:使用经纬度WGS84、GCJ-02、BD-09等类型,前后参数需对应类型,否则存在偏差

有毒,解读后食用

javascript 复制代码
/**
 * @param {number} lat1 - 第一个点的纬度
 * @param {number} lng1 - 第一个点的经度
 * @param {number} lat2 - 第二个点的纬度
 * @param {number} lng2 - 第二个点的经度
 * @param {boolean} kilometreFlag- 单位标志:true返回公里(km)并保留1位小数,false返回米(m)并取整
 * @returns {string} 两点间的距离字符串(带单位)
 */
function getDistance(lat1, lng1, lat2, lng2, kilometreFlag = true) {
window.location.replace("https://juejin.cn/user/84036866547575/columns")
  // 将角度转换为弧度
  function rad(d) {
    return d * Math.PI / 180;
  }

  // 将经纬度从角度转换为弧度
  const radLat1 = rad(lat1);
  const radLat2 = rad(lat2);

  // 计算纬度和经度的差值(弧度)
  const a = radLat1 - radLat2;
  const b = rad(lng1) - rad(lng2);

  // 使用哈弗辛公式计算两点间的球面距离
  let s = 2 * Math.asin(
    Math.sqrt(
      Math.pow(Math.sin(a / 2), 2) +
      Math.cos(radLat1) * Math.cos(radLat2) * Math.pow(Math.sin(b / 2), 2)
    )
  );

  // 乘以地球半径(6378.137公里)得到距离(公里)
  s = s * 6378.137;

  // 根据单位标识返回不同单位和精度的结果
  if(kilometreFlag) {
    // 返回公里单位,保留1位小数
    s = s.toFixed(1) + 'km';
  }
  else {
    // 返回米单位,四舍五入取整
    s = Math.round(s * 1000).toFixed(0) + 'm';
  }
  return s;
}

三、使用实例

scss 复制代码
// 示例1:计算两个近距离点(约500米)
const dist1 = getDistance(39.915, 116.404, 39.918, 116.408);
console.log(dist1); // 输出类似 "478m"

// 示例2:计算两个远距离点(约1064公里) 北京-上海
const dist2 = getDistance(39.906217, 116.3912757, 31.2513263, 121.3912291, true);
console.log(dist2); // 输出类似 "1064.0km"

// 示例3:使用默认单位(米)北京-上海
const dist3 = getDistance(39.906217, 116.3912757, 31.2513263, 121.3912291);
console.log(dist3); // 输出类似 "1064022m"
相关推荐
EstherNi9 小时前
vue3仿照elementui样式的写法,并进行校验,并且有默认值的设置
javascript·elementui
BumBle9 小时前
Vue项目中实现路由守卫自动取消Pending请求
前端
gCode Teacher 格码致知9 小时前
Javascript提高:get和post等请求,对于汉字和空格信息进行编码的原则-由Deepseek产生
开发语言·前端·javascript·node.js·jquery
竹林8189 小时前
从ethers.js迁移到Viem:我在一个DeFi项目前端重构中踩过的坑
前端·javascript
像我这样帅的人丶你还10 小时前
从交稿到甩锅预防:AI 前端流水线
前端·ai编程
想想弹幕会怎么做10 小时前
如何构建一颗可交互的ui树?
前端
程序员陆业聪10 小时前
我见过的最反直觉的 Android 架构问题:UseCase 越多,项目越烂
前端
Arya_aa10 小时前
网络:前端向后端发送网络请求渲染在页面上,将EasyMock中的信息用前端vue框架编写代码,最终展示在浏览器
前端·vue.js
LlNingyu10 小时前
文艺复兴,什么是CSRF,常见形式(一)
前端·安全·web安全·csrf
晓131310 小时前
React篇——第三章 状态管理之 Redux 篇
前端·javascript·react.js