设为首页 收藏本站
查看: 864|回复: 0

[经验分享] 使用Python实现子区域数据分类统计

[复制链接]

尚未签到

发表于 2018-8-14 11:32:37 | 显示全部楼层 |阅读模式
一、前言
  最近碰到一个需求,需要统计某省内的所有市的某数据分布情况信息。现有该省的数据分布情况以及该省的行政区划数据。我通过geopandas库实现了这一需求,在这里简单记录之,供需要的人借鉴。
二、geopandas简介
  想必大家对pandas都不陌生,它是一个开源的强大的Python数据分析工具。pandas确实做到了灵活、快速、高效的进行数据处理,而geopandas是在pandas的基础上添加了对空间数据的支持,实现了读取空间数据以及对空间数据进行处理。关于其介绍和安装等请参考其github主页,本文不再赘述。
三、子区域数据分类统计
  直接进入正题,现有某省的分类统计数据shp文件以及此省的行政区划数据shp文件。
3.1 引入geopandas
  为了使用geopandas库,首先需要将其引入。代码如下:
from geopandas import *3.2 读取此省分类统计数据及行政区划数据
  然后从该省的分类统计数据shp文件中读出此数据。代码如下:
provincedata = GeoDataFrame.from_file(provinceshpfile)  代码很简单,只要给GeoDataFrame.from_file函数传入shp文件路径即可,其得到的是一个GeoDataFrame对象,类似于pandas中的DataFrame,区别会在下文讲到。同理,行政区划数据通过以下代码读入:
regiondata = GeoDataFrame.from_file(regionshppath)3.3 投影转换
  要使上述两个数据能够进行处理必须先要将其转换成相同的投影。geopandas进行投影转换很简单。代码如下:
gpd_new=gpd.to_crs(crs)  其中gpd表示原始数据,gpd_new为转换后的数据,crs表示需要转换的投影参数,在https://github.com/geopandas/geopandas/blob/46e50fe5a772944b325bc3c8806f4f96da76a0d8/doc/source/projections.rst中对此参数进行了详细描述,大家可以参照。
  所以我们只需要将上述两种数据转换到同一投影即可,问题是假设我们不知道它们的投影类型,那么也很容易,只需要将其都转换成4326或其他投影即可,这样就能保证二者转换后为同一投影。但是问题又来了,如果该省分类数据特别大将会导致投影转换耗时过长。其实此处有个简单方法,我们只需要读出分类数据的crs并将行政区划数据转换成此投影即可,这样不仅代码简单而且能够节省大量时间。代码如下:
regiondata_crs = regiondata.to_crs(provincedata.crs)3.4 对该省逐市进行数据分类提取
  现在二者投影已经相同,我们不得不面对最核心的问题,如何能够从省的分类数据中提取出逐市分类数据情况。我们可以想到必须要将每个市的空间数据与该省的所有分类数据进行相交判断,判断哪些分类数据与该市相交,然后完成相应处理。
3.4.1 获取市的空间数据
  首先对行政区划数据进行循环得到每个市的空间数据。代码如下:
for i in range(0, len(regiondata_crs)):  
    geo = regiondata_crs.geometry
  
    name = regiondata_crs.NAME
  其中geo就是取到的当前市的空间数据,可以看出GeoDataFrame与DataFrame的区别就在于多了一个geometry字段,它包含了数据的空间信息,可以对该字段进行空间操作。假设该shp文件还包含了一个NAME属性,那么我们就可以用“.NAME”的方式提取出当前市的name数据,其他属性同理。
3.4.2 获取此空间内的分类数据信息
  有了geo之后就可以将其与省的分类数据中的每一个对象进行相交判断(循环判断),根据结果进行相应处理。这里我们假设统计不同种类数据的面积值,即每种类型的数据在该市所占面积大小。代码如下:
area = {}for i in range(0, len(provincedata)):  
    geo_province = provincedata.geometry    id = str(provincedata.ID)    if geo_province.intersects(geo) and geo_province.is_valid :
  
        temp_geo = geo_province.intersection(geo)
  
        temp_area = temp_geo.area        if area.get(id) == None:
  
            area[id] = temp_area        else :
  
            area[id] = area.get(id) + temp_area
  其中area为字典对象,用来存储不同数据在该市所占面积。
  首先通过provincedata.geometry获取该数据的空间信息geo_province,然后使用provincedata.ID取出该数据的编号值id。
  geo_province.intersects(geo)用来判断该数据与当前市(geo)在空间上是否相交,geo_province.is_valid用来判断该数据是否合法,有无自相交环等。
  如果相交则进行处理,首先通过geo_province.intersection(geo)来获取相交的部分temp_geo,然后通过temp_geo.area获取相交部分的面积temp_area。可以看出在geopandas中只需要对geometry对象使用area属性即可获取其面积。
  最后将面积以id为key保存到area字典当中。
四、总结
  这样就可以实现对该省的分类统计数据进行进一步细分,取出每个市的数据分类信息。当然并一定局限于省和市,比如全球和国家或者国家和省等。只要存在包含关系即可通过此种方式进行处理。这是鸡年的第一篇博客,愿所有人今年都能有个好的结果!

运维网声明 1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com

所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其承担任何法律责任,如涉及侵犯版权等问题,请您及时通知我们,我们将立即处理,联系人Email:kefu@iyunv.com,QQ:1061981298 本贴地址:https://www.yunweiku.com/thread-551589-1-1.html 上篇帖子: 使用Python爬取煎蛋网妹纸图片 下篇帖子: python常用模块使用分析
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

扫码加入运维网微信交流群X

扫码加入运维网微信交流群

扫描二维码加入运维网微信交流群,最新一手资源尽在官方微信交流群!快快加入我们吧...

扫描微信二维码查看详情

客服E-mail:kefu@iyunv.com 客服QQ:1061981298


QQ群⑦:运维网交流群⑦ QQ群⑧:运维网交流群⑧ k8s群:运维网kubernetes交流群


提醒:禁止发布任何违反国家法律、法规的言论与图片等内容;本站内容均来自个人观点与网络等信息,非本站认同之观点.


本站大部分资源是网友从网上搜集分享而来,其版权均归原作者及其网站所有,我们尊重他人的合法权益,如有内容侵犯您的合法权益,请及时与我们联系进行核实删除!



合作伙伴: 青云cloud

快速回复 返回顶部 返回列表