【Maxcompute】bd09、gcj02、wgs84经纬度坐标系转换udf函数

本文涉及的产品
云原生大数据计算服务 MaxCompute,5000CU*H 100GB 3个月
云原生大数据计算服务MaxCompute,500CU*H 100GB 3个月
简介: 该文介绍了在Maxcompute平台上处理经纬度的实战应用,包括`bd09`、`gcj02`和`wgs84`坐标系之间的转换。提供了`CoordTransform` Python UDF类,支持六种转换操作。代码中包含了转换方法如`bd09togcj02`等,以及辅助计算静态方法。欢迎读者批评指正。

1.梳理、总结经纬度处理在Maxcompute平台上的实战应用,如bd09、gcj02、wgs84经纬度坐标系转换UDF函数注册与使用。
2.欢迎批评指正,跪谢一键三连!

1.参考代码

  • 坐标系转换
    • bd09坐标系(百度坐标系)gcj02坐标系(中国国家测绘局(g表示guojia国家,c表示cehui测绘,j表示ju局)制订的地理信息系统的坐标系统)
    • gcj02坐标系(中国国家测绘局(g表示guojia国家,c表示cehui测绘,j表示ju局)制订的地理信息系统的坐标系统)转bd09坐标系(百度坐标系)
    • bd09坐标系(百度坐标系)地球坐标系(world geodetic system)
    • 地球坐标系(world geodetic system)gcj02坐标系(中国国家测绘局(g表示guojia国家,c表示cehui测绘,j表示ju局)制订的地理信息系统的坐标系统)
    • gcj02坐标系(中国国家测绘局(g表示guojia国家,c表示cehui测绘,j表示ju局)制订的地理信息系统的坐标系统)地球坐标系(world geodetic system)
    • 地球坐标系(world geodetic system)bd09坐标系(百度坐标系)
  •   # coding:utf-8
      from odps.udf import annotate
      import math
    
      @annotate("double,double,string,string->string")
      class CoordTransform(object):
          '''
          function: 坐标系转换
          input:  lng,lat,src,dest
          parms:  lng:经度 double
                  lat:纬度 double
                  src:输入坐标系 ['bd','gcj','wgs']
                  dest:输出坐标系 ['bd','gcj','wgs']
          output:string: 'lng,lat'
          '''
          def evaluate(self, lng, lat, src, dest):
              if src == 'bd' and dest == 'gcj':
                  return ','.join([str(x) for x in GeoUtils.bd09togcj02(float(lng), lat)])
              elif src == 'bd' and dest == 'wgs':
                  # return GeoUtils.bd09towgs84(lng,lat)
                  return ','.join([str(x) for x in GeoUtils.bd09towgs84(lng, lat)])
              elif src == 'gcj' and dest == 'wgs':
                  return ','.join([str(x) for x in GeoUtils.gcj02towgs84(lng, lat)])
              elif src == 'gcj' and dest == 'bd':
                  return ','.join([str(x) for x in GeoUtils.gcj02tobd09(lng, lat)])
    
              elif src == 'wgs' and dest == 'bd':
                  return ','.join([str(x) for x in GeoUtils.wgs84tobd09(lng, lat)])
    
              if src == 'wgs' and dest == 'gcj':
                  return ','.join([str(x) for x in GeoUtils.wgs84togcj02(lng, lat)])
    
      class GeoUtils():
          PI = 3.1415926535897932384626
          a = 6378245.0
          ee = 0.00669342162296594323
          @staticmethod
          def bd09togcj02(bd_lng, bd_lat):
              """bd09坐标系(百度坐标系)转gcj02坐标系(中国国家测绘局(g表示guojia国家,c表示cehui测绘,j表示ju局)制订的地理信息系统的坐标系统)"""
              x = bd_lng - 0.0065
              y = bd_lat - 0.006
              z = math.sqrt(x * x + y * y) - 0.00002 * math.sin(y * GeoUtils.PI)
              theta = math.atan2(y, x) - 0.000003 * math.cos(x * GeoUtils.PI)
              gcj_lng = z * math.cos(theta)
              gcj_lat = z * math.sin(theta)
              return [gcj_lng, gcj_lat]
          @staticmethod
          def gcj02tobd09(gcj_lng, gcj_lat):
              """gcj02坐标系(中国国家测绘局(g表示guojia国家,c表示cehui测绘,j表示ju局)制订的地理信息系统的坐标系统)转bd09坐标系(百度坐标系)"""
              z = math.sqrt(gcj_lng * gcj_lng + gcj_lat * gcj_lat) + 0.00002 * math.sin(gcj_lat * GeoUtils.PI)
              theta = math.atan2(gcj_lat, gcj_lng) + 0.000003 * math.cos(gcj_lng * GeoUtils.PI)
              bd_lng = z * math.cos(theta) + 0.0065
              bd_lat = z * math.sin(theta) + 0.006
              return [bd_lng, bd_lat]
          @staticmethod
          def bd09towgs84(lng, lat):
              """bd09坐标系(百度坐标系)转地球坐标系(world geodetic system)"""
              return GeoUtils.gcj02towgs84(*GeoUtils.bd09togcj02(lng, lat))
          @staticmethod
          def wgs84togcj02(lng, lat):
              """地球坐标系(world geodetic system)转gcj02坐标系(中国国家测绘局(g表示guojia国家,c表示cehui测绘,j表示ju局)制订的地理信息系统的坐标系统)"""
              dlat = GeoUtils.transformlat(lng - 105.0, lat - 35.0)
              dlng = GeoUtils.transformlng(lng - 105.0, lat - 35.0)
              radlat = lat / 180.0 * GeoUtils.PI
              magic = math.sin(radlat)
              magic = 1 - GeoUtils.ee * magic * magic
              sqrtmagic = math.sqrt(magic)
              dlat = (dlat * 180.0) / ((GeoUtils.a * (1 - GeoUtils.ee)) / (magic * sqrtmagic) * GeoUtils.PI)
              dlng = (dlng * 180.0) / (GeoUtils.a / sqrtmagic * math.cos(radlat) * GeoUtils.PI)
              mglat = lat + dlat
              mglng = lng + dlng
              return [mglng, mglat]
          @staticmethod
          def gcj02towgs84(lng, lat):
              """gcj02坐标系(中国国家测绘局(g表示guojia国家,c表示cehui测绘,j表示ju局)制订的地理信息系统的坐标系统)转地球坐标系(world geodetic system)"""
              dlat = GeoUtils.transformlat(lng - 105.0, lat - 35.0)
              dlng = GeoUtils.transformlng(lng - 105.0, lat - 35.0)
              radlat = lat / 180.0 * GeoUtils.PI
              magic = math.sin(radlat)
              magic = 1 - GeoUtils.ee * magic * magic
              sqrtmagic = math.sqrt(magic)
              dlat = (dlat * 180.0) / ((GeoUtils.a * (1 - GeoUtils.ee)) / (magic * sqrtmagic) * GeoUtils.PI)
              dlng = (dlng * 180.0) / (GeoUtils.a / sqrtmagic * math.cos(radlat) * GeoUtils.PI)
              mglat = lat + dlat
              mglng = lng + dlng
              return [lng * 2 - mglng, lat * 2 - mglat]
          @staticmethod
          def wgs84tobd09(lng, lat):
              """地球坐标系(world geodetic system)转bd09坐标系(百度坐标系)"""
              dlat = GeoUtils.transformlat(lng - 105.0, lat - 35.0)
              dlng = GeoUtils.transformlng(lng - 105.0, lat - 35.0)
              radlat = lat / 180.0 * GeoUtils.PI
              magic = math.sin(radlat)
              magic = 1 - GeoUtils.ee * magic * magic
              sqrtmagic = math.sqrt(magic)
              dlat = (dlat * 180.0) / ((GeoUtils.a * (1 - GeoUtils.ee)) / (magic * sqrtmagic) * GeoUtils.PI)
              dlng = (dlng * 180.0) / (GeoUtils.a / sqrtmagic * math.cos(radlat) * GeoUtils.PI)
              mglat = lat + dlat
              mglng = lng + dlng
              z = math.sqrt(mglng * mglng + mglat * mglat) + 0.00002 * math.sin(mglat * GeoUtils.PI)
              theta = math.atan2(mglat, mglng) + 0.000003 * math.cos(mglng * GeoUtils.PI)
              bd_lng = z * math.cos(theta) + 0.0065
              bd_lat = z * math.sin(theta) + 0.006
              return [bd_lng, bd_lat]
          @staticmethod
          def transformlat(lng, lat):
              ret = -100.0 + 2.0 * lng + 3.0 * lat + 0.2 * lat * lat + 0.1 * lng * lat + 0.2 * math.sqrt(abs(lng))
              ret += (20.0 * math.sin(6.0 * lng * GeoUtils.PI) + 20.0 * math.sin(2.0 * lng * GeoUtils.PI)) * 2.0 / 3.0
              ret += (20.0 * math.sin(lat * GeoUtils.PI) + 40.0 * math.sin(lat / 3.0 * GeoUtils.PI)) * 2.0 / 3.0
              ret += (160.0 * math.sin(lat / 12.0 * GeoUtils.PI) + 320 * math.sin(lat * GeoUtils.PI / 30.0)) * 2.0 / 3.0
              return ret
          @staticmethod
          def transformlng(lng, lat):
              ret = 300.0 + lng + 2.0 * lat + 0.1 * lng * lng + 0.1 * lng * lat + 0.1 * math.sqrt(abs(lng))
              ret += (20.0 * math.sin(6.0 * lng * GeoUtils.PI) + 20.0 * math.sin(2.0 * lng * GeoUtils.PI)) * 2.0 / 3.0
              ret += (20.0 * math.sin(lng * GeoUtils.PI) + 40.0 * math.sin(lng / 3.0 * GeoUtils.PI)) * 2.0 / 3.0
              ret += (150.0 * math.sin(lng / 12.0 * GeoUtils.PI) + 300.0 * math.sin(lng / 30.0 * GeoUtils.PI)) * 2.0 / 3.0
              return ret
          @staticmethod
          def outofchina(lng, lat):
              """
              判断是否在国内,不在国内不做处理,异常点位
              :param lng:
              :param lat:
              :return:
              """
              return not (lng > 73.66 and lng < 135.05 and lat > 3.86 and lat < 53.55)
    
相关实践学习
基于MaxCompute的热门话题分析
本实验围绕社交用户发布的文章做了详尽的分析,通过分析能得到用户群体年龄分布,性别分布,地理位置分布,以及热门话题的热度。
SaaS 模式云数据仓库必修课
本课程由阿里云开发者社区和阿里云大数据团队共同出品,是SaaS模式云原生数据仓库领导者MaxCompute核心课程。本课程由阿里云资深产品和技术专家们从概念到方法,从场景到实践,体系化的将阿里巴巴飞天大数据平台10多年的经过验证的方法与实践深入浅出的讲给开发者们。帮助大数据开发者快速了解并掌握SaaS模式的云原生的数据仓库,助力开发者学习了解先进的技术栈,并能在实际业务中敏捷的进行大数据分析,赋能企业业务。 通过本课程可以了解SaaS模式云原生数据仓库领导者MaxCompute核心功能及典型适用场景,可应用MaxCompute实现数仓搭建,快速进行大数据分析。适合大数据工程师、大数据分析师 大量数据需要处理、存储和管理,需要搭建数据仓库?学它! 没有足够人员和经验来运维大数据平台,不想自建IDC买机器,需要免运维的大数据平台?会SQL就等于会大数据?学它! 想知道大数据用得对不对,想用更少的钱得到持续演进的数仓能力?获得极致弹性的计算资源和更好的性能,以及持续保护数据安全的生产环境?学它! 想要获得灵活的分析能力,快速洞察数据规律特征?想要兼得数据湖的灵活性与数据仓库的成长性?学它! 出品人:阿里云大数据产品及研发团队专家 产品 MaxCompute 官网 https://www.aliyun.com/product/odps&nbsp;
目录
相关文章
|
2月前
|
分布式计算 DataWorks 大数据
MaxCompute产品使用合集之如何使用UDF来使用Protocol Buffers
MaxCompute作为一款全面的大数据处理平台,广泛应用于各类大数据分析、数据挖掘、BI及机器学习场景。掌握其核心功能、熟练操作流程、遵循最佳实践,可以帮助用户高效、安全地管理和利用海量数据。以下是一个关于MaxCompute产品使用的合集,涵盖了其核心功能、应用场景、操作流程以及最佳实践等内容。
49 15
|
2月前
|
分布式计算 自然语言处理 大数据
MaxCompute操作报错合集之使用pyodps读取全表(百万级),然后对其中某列apply自己定义的分词函数,遇到报错,该如何排查
MaxCompute是阿里云提供的大规模离线数据处理服务,用于大数据分析、挖掘和报表生成等场景。在使用MaxCompute进行数据处理时,可能会遇到各种操作报错。以下是一些常见的MaxCompute操作报错及其可能的原因与解决措施的合集。
|
2月前
|
SQL 分布式计算 数据处理
MaxCompute操作报错合集之使用Spark查询时函数找不到的原因是什么
MaxCompute是阿里云提供的大规模离线数据处理服务,用于大数据分析、挖掘和报表生成等场景。在使用MaxCompute进行数据处理时,可能会遇到各种操作报错。以下是一些常见的MaxCompute操作报错及其可能的原因与解决措施的合集。
|
2月前
|
分布式计算 DataWorks 数据处理
MaxCompute操作报错合集之UDF访问OSS,配置白名单后出现报错,是什么原因
MaxCompute是阿里云提供的大规模离线数据处理服务,用于大数据分析、挖掘和报表生成等场景。在使用MaxCompute进行数据处理时,可能会遇到各种操作报错。以下是一些常见的MaxCompute操作报错及其可能的原因与解决措施的合集。
|
2月前
|
分布式计算 大数据 数据处理
MaxCompute操作报错合集之编写UDF(用户自定义函数)时,报错:找不到主类,是什么原因
MaxCompute是阿里云提供的大规模离线数据处理服务,用于大数据分析、挖掘和报表生成等场景。在使用MaxCompute进行数据处理时,可能会遇到各种操作报错。以下是一些常见的MaxCompute操作报错及其可能的原因与解决措施的合集。
|
2月前
|
分布式计算 监控 大数据
MaxCompute产品使用合集之CASE WHEN语句如何开窗函数一起使用
MaxCompute作为一款全面的大数据处理平台,广泛应用于各类大数据分析、数据挖掘、BI及机器学习场景。掌握其核心功能、熟练操作流程、遵循最佳实践,可以帮助用户高效、安全地管理和利用海量数据。以下是一个关于MaxCompute产品使用的合集,涵盖了其核心功能、应用场景、操作流程以及最佳实践等内容。
|
2月前
|
机器学习/深度学习 分布式计算 大数据
MaxCompute产品使用合集之是否可以将5个资源包统一写到同一个python UDF脚本
MaxCompute作为一款全面的大数据处理平台,广泛应用于各类大数据分析、数据挖掘、BI及机器学习场景。掌握其核心功能、熟练操作流程、遵循最佳实践,可以帮助用户高效、安全地管理和利用海量数据。以下是一个关于MaxCompute产品使用的合集,涵盖了其核心功能、应用场景、操作流程以及最佳实践等内容。
|
2月前
|
SQL 分布式计算 DataWorks
MaxCompute操作报错合集之在创建SQL函数时,遇到报错,该如何解决
MaxCompute是阿里云提供的大规模离线数据处理服务,用于大数据分析、挖掘和报表生成等场景。在使用MaxCompute进行数据处理时,可能会遇到各种操作报错。以下是一些常见的MaxCompute操作报错及其可能的原因与解决措施的合集。
155 0
|
2月前
|
分布式计算 大数据 数据处理
MaxCompute操作报错合集之在使用udf遇到报错,是什么原因
MaxCompute是阿里云提供的大规模离线数据处理服务,用于大数据分析、挖掘和报表生成等场景。在使用MaxCompute进行数据处理时,可能会遇到各种操作报错。以下是一些常见的MaxCompute操作报错及其可能的原因与解决措施的合集。
|
3月前
|
机器学习/深度学习 分布式计算 DataWorks
MaxCompute产品使用问题之如何在UDF函数中访问外网
MaxCompute作为一款全面的大数据处理平台,广泛应用于各类大数据分析、数据挖掘、BI及机器学习场景。掌握其核心功能、熟练操作流程、遵循最佳实践,可以帮助用户高效、安全地管理和利用海量数据。以下是一个关于MaxCompute产品使用的合集,涵盖了其核心功能、应用场景、操作流程以及最佳实践等内容。