《Python地理空间分析指南 第2版》学习笔记-5.5Shapefile文件编辑-下

13 篇文章 4 订阅
6 篇文章 0 订阅

《Python地理空间分析指南 第2版》学习笔记-5.5Shapefile文件编辑-下

往期内容请看

《Python地理空间分析指南 第2版》学习笔记-5.5Shapefile文件编辑-上

《Python地理空间分析指南 第2版》学习笔记-5.5Shapefile文件编辑-中

5.5.5Shapefile文件合并

使用一组某城市分布于4个不同方位(西北、东北、西南和东南)的建筑物轮廓分布
图,合并成一幅。
在这里插入图片描述

方法一:shapefile文件合并

import glob
import shapefile

# 读取相同字符footprints_*shp的矢量文件
filename = glob.glob(r"footprints\footprints_*shp")
#创建要写入的对象
with shapefile.Writer(r"footprints\merge") as w:
    r = None
    for f in filename:
        r = shapefile.Reader(f)
        #写入字段
        if not w.fields:
            w.fields = list(r.fields)
        #写入记录
        for rec in r.records():
            w.record(*list(rec))
        #写入形状
        for s in r.shapes():
            w._shapeparts(parts =[s.points],shapeType=s.shapeType )

结果展示:
在这里插入图片描述

方法二:使用dfbpy合并Shapefile文件

OGR库和pyshp库都能读写dbf文件,因为dbf文件都是shapefile文件规范的一部分。dbf文件包含shapefile文件的属性和字段信息,但是OGR库和pyshp库只提供了对dbf文件的基本操作。若需要对dbf文件进行更复杂的操作,需要自己手动安装dbfpy3库。
dbfpy3-4.1.5-py2.py3-none-any.whl

import glob
import shapefile
from dbfpy3 import dbf

shp_files = glob.glob("footprints_*.shp")
w = shapefile.Writer(shp="merged.shp", shx="merged.shx")
# 新建merged.shp,将各个部分文件,循环写入merged.shp中

for f in shp_files:
    print("Shp: {}".format(f))
    r = shapefile.Reader(f)
    # r = shapefile.Reader(shp=shpf)
    for s in r.shapes():
        w.poly([s.points])

w.close()

# 思路:
# Now we come back with dbfpy and merge the dbf files
dbf_files = glob.glob("*.dbf")
# Use the first dbf file as a template
template = dbf_files.pop(0)
merged_dbf_name = "merged.dbf"
# Copy the entire template dbf file to the merged file
merged_dbf = open(merged_dbf_name, "wb")
temp = open(template, "rb")
merged_dbf.write(temp.read())
merged_dbf.close()
temp.close()

# Now read each record from teh remaining dbf files
# and use the contents to create a new record in
# the merged dbf file.
db = dbf.Dbf(merged_dbf)

for f in dbf_files:
    print("Dbf: {}".format(f))
    dba = dbf.Dbf(f)
    for rec in dba:
        db_rec = db.newRecord()
        for k, v in list(rec.asDict().items()):
            db_rec[k] = v
        db_rec.store()
db.close()

5.5.6Shapefile文件分割

有时,你也许需要从一个比较大的Shapefile文件中分割出一个特定的子文件,以便将重点放在感兴趣的部分。这些分割和子集化操作可以是空间方面的,也可以是感兴趣的特定属性方面
的。

下面的案例,根据区域对建筑物分布图进行过滤并将导出大约100平方米的建筑物分布图到一个新的Shapefile文件
中。


import shapefile
import utm

# 读取矢量面文件
r = shapefile.Reader(r"footprints\footprints_se")
# 创建新的矢量面对象 w
with shapefile.Writer(r"footprints\footprints_sp100", r.shapeType) as w:
    # 将字段复制给w
    w.fields = list(r.fields)
    # 遍历r记录
    for sr in r.shapeRecords():
        utmPoints = []
        for p in sr.shape.points:
            x, y, band, zone = utm.from_latlon(p[1], p[0])
            utmPoints.append([x, y])
            # print(utmPoints)
        # 计算每个矢量面的坐标
        area = abs(shapefile.signed_area(utmPoints))
        # print(area)
        if area <= 100:
            w.poly([sr.shape.points])
            w.record(*list(sr.record))
# 结果验证
r = shapefile.Reader(r"footprints\footprints_se")
subset = shapefile.Reader(r"footprints\footprints_sp100")
print("总数:",r.numRecords)
print("子集:",subset.numRecords)

结果
总数: 26447
子集: 13331

footprints_se文件
在这里插入图片描述

footprints_sp100文件:建筑面积小于100平方米
在这里插入图片描述


结束语

《Python地理空间分析指南 第2版》学习笔记,仅供学习,如有侵权请联系删除。

  • 3
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值