一、问题说明
项目中集成百度地图API和高德API的时候。定位总是有偏移,这是就需要坐标转换。由此引出本文的话题,为什么我的坐标,在地图上显示会有偏移?各种坐标体系之间如何转换?到底有哪些坐标体系?什么是火星坐标?
坐标系统:用于定位的系统,就跟二维笛卡尔坐标系统一样,一个点使用(x,y),就能确定该点在笛卡尔坐标系统中的唯一位置。这里讲的坐标系统,相对于笛卡尔坐标系统,要复杂许多,但作用却都是一样,主要用于定位,也就是精确地定位地表上的一点。
地理坐标系统:WGS84就是一种地理坐标系统。地理坐标坐标是对地球进行简单几何建模,比如将地球看成一个球体或者类球体,然后再将地表上点投影到该球面上形成的坐标就是地理坐标系统。WGS84就是定义了如何将地球抽象成球体或者类球体的规则。或者简单地来说,WGS84就是一堆参数,用于建立球体或者类球体,来近似地球。
投影坐标系统:由于地球是一个球状,所以一般将其某个区域投影在平面上,形成的坐标系称为投影坐标系。
WGS84 :地理坐标系统,Google Earth和中国外的Google Map使用,另外,目前基本上所有定位空间位置的设备都使用这种坐标系统,例如手机的GPS系统。
GCJ-02:投影坐标系统,也就是我们平常所说的火星坐标系,Google Map中国、高德和腾讯好像使用,这个是中国自己在WGS84基础上加密而成,目的显而易见。
BD09:投影坐标系统,百度地图使用,在GCJ-02基础上二次加密而成。
国内各地图API坐标系统比较
二、代码实现
longitude 经度 latitude 纬度
1、算法实现
public class Map {
public static double pi = 3.1415926535897932384626;
public static double x_pi = 3.14159265358979324 * 3000.0 / 180.0;
public static double a = 6378245.0;
public static double ee = 0.00669342162296594323;
/**
* 高德 == 》 百度
* @param lat
* @param lon
*/
public static double[] gcj02_To_Bd09(double lat, double lon) {
double x = lon, y = lat;
double z = Math.sqrt(x * x + y * y) + 0.00002 * Math.sin(y * x_pi);
double theta = Math.atan2(y, x) + 0.000003 * Math.cos(x * x_pi);
double tempLon = z * Math.cos(theta) + 0.0065;
double tempLat = z * Math.sin(theta) + 0.006;
double[] gps = {tempLat,tempLon};
return gps;
}
/**
* 百度 == 》 高德
* @param lat
* @param lon
*/
public static double[] bd09_To_Gcj02(double lat, double lon) {
double x = lon - 0.0065, y = lat - 0.006;
double z = Math.sqrt(x * x + y * y) - 0.00002 * Math.sin(y * x_pi);
double theta = Math.atan2(y, x) - 0.000003 * Math.cos(x * x_pi);
double tempLon = z * Math.cos(theta);
double tempLat = z * Math.sin(theta);
double[] gps = {tempLat,tempLon};
return gps;
}
}