美文网首页物联网
关于高德地图、google地图转换为GPS真实坐标方法

关于高德地图、google地图转换为GPS真实坐标方法

作者: Monkey_hbh | 来源:发表于2017-08-16 10:55 被阅读2299次

    最近一直研究地图,包括高德、google、百度、google earth地图,经常使用地图的也会发现,其实高德地图、百度地图、google地图和GPS获取的坐标差异很大,那怎么转换呢,我们一步一步分析:

    坐标体系

    1、GPS,WGS-84,原始坐标体系。一般用国际标准的GPS记录仪记录下来的坐标,都是GPS的坐标。很可惜,在中国,任何一个地图产品都不允许使用GPS坐标,据说是为了保密。
    2、 GCJ-02,国测局02年发布的坐标体系。又称“火星坐标”。在中国,必须至少使用GCJ-02的坐标体系。比如谷歌,腾讯,高德都在用这个坐标体系。GCJ-02也是国内最广泛使用的坐标体系。
    3、其他坐标体系。一般都是由GCJ-02进过偏移算法得到的。这种体系就根据每个公司的不同,坐标体系都不一样了。比如,百度和搜狗就使用自己的坐标体系,与其他坐标体系不兼容

    注解:所有坐标系的原点都是非洲

    从上面三种坐标系我们就可以大概知道为啥地图之前和google earth地图有差异(google earth地图和GPS获取的坐标一致)
    在各种web端平台,或者高德、腾讯、百度上取到的坐标,都不是GPS坐标,都是GCJ-02坐标,或者自己的偏移坐标系。
    比如,你在谷歌地图API,高德地图API,腾讯地图API上取到的,都是GCJ-02坐标,他们三家都是通用的,也适用于大部分地图API产品,以及他们的地图产品。
    例外,百度API上取到的,是BD-09坐标,只适用于百度地图相关产品。
    例外,搜狗API上取到的,是搜狗坐标,只适用于搜狗地图相关产品。
    例外,谷歌地球,google earth上取到的,是GPS坐标,而且是度分秒形式的经纬度坐标。在国内不允许使用。必须转换为GCJ-02坐标。

    所以接下来我们就看看怎么将GCJ-02坐标转换为GPS的WGS-84坐标:

    static double pointA = 6378245.0;
    static double pi = 3.14159265358979324;
    static double ee = 0.00669342162296594323;
    
    - (CLLocationCoordinate2D )changePointToWGS84PointwithLatitude:(double)latitude longitude:(double)longitude
    {
        CLLocationCoordinate2D dev = [self calDevWithwgLon:longitude wglat:latitude];
        double retLat = latitude - dev.latitude;
        double retLon = longitude - dev.longitude;
        dev = [self calDevWithwgLon:retLon wglat:retLat];
        retLat = latitude - dev.latitude;
        retLon = longitude - dev.longitude;
        return CLLocationCoordinate2DMake(retLat, retLon);
    }
    
    - (CLLocationCoordinate2D )calDevWithwgLon:(double)wglon wglat:(double)wglat
    {
        if ([self isOutOfChinaWithlat:wglat lon:wglon]) {
            return CLLocationCoordinate2DMake(0, 0);
        }
        double dLat = [self calLatWithX:wglon - 105.0 Y:wglat - 35.0];
        double dLon = [self calLonWithX:wglon - 105.0 Y:wglat - 35.0];
        double radLat = wglat / 180.0 * pi;
        double magic = sin(radLat);
        magic = 1 - ee * magic * magic;
        double sqrtMagic = sqrt(magic);
        dLat = (dLat * 180.0) / ((pointA * (1 - ee)) / (magic * sqrtMagic) * pi);
        dLon = (dLon * 180.0) / (pointA / sqrtMagic * cos(radLat) * pi);
        return CLLocationCoordinate2DMake(dLat, dLon);
    }
    
    - (BOOL)isOutOfChinaWithlat:(double)lat lon:(double)lon
    {
        if (lon < 72.004 || lon > 137.8347)
            return true;
        if (lat < 0.8293 || lat > 55.8271)
            return true;
        return false;
    }
    
    - (double)calLatWithX:(double)x Y:(double)y
    {
        double ret = -100.0 + 2.0 * x + 3.0 * y + 0.2 * y * y + 0.1 * x * y + 0.2
        * sqrt(fabs(x));
        ret += (20.0 * sin(6.0 * x * pi) + 20.0 * sin(2.0 * x * pi)) * 2.0 / 3.0;
        ret += (20.0 * sin(y * pi) + 40.0 * sin(y / 3.0 * pi)) * 2.0 / 3.0;
        ret += (160.0 * sin(y / 12.0 * pi) + 320 * sin(y * pi / 30.0)) * 2.0 / 3.0;
        return ret;
    }
    
    - (double)calLonWithX:(double)x Y:(double)y
    {
        double ret = 300.0 + x + 2.0 * y + 0.1 * x * x + 0.1 * x * y + 0.1 * sqrt(fabs(x));
        ret += (20.0 * sin(6.0 * x * pi) + 20.0 * sin(2.0 * x * pi)) * 2.0 / 3.0;
        ret += (20.0 * sin(x * pi) + 40.0 * sin(x / 3.0 * pi)) * 2.0 / 3.0;
        ret += (150.0 * sin(x / 12.0 * pi) + 300.0 * sin(x / 30.0 * pi)) * 2.0 / 3.0;
        return ret;
    }
    

    OK了、这样就成功将GCJ-02坐标转换为WGS-84坐标了,顺便附上查询坐标验证网址,大家可以试试:http://www.gpsspg.com/maps.htm
    如有错误麻烦指点一二。对于WGS-84转换为GCJ-02将在之后更新。

    相关文章

      网友评论

        本文标题:关于高德地图、google地图转换为GPS真实坐标方法

        本文链接:https://www.haomeiwen.com/subject/jmtirxtx.html