如何在Excel/QGIS中快速批量标记坐标所属的多边形区域?
批量判断坐标所属多边形的高效方法
我有一份Excel存储的销售线索坐标列表,需要判断每个坐标是否在指定多边形(如城市边界)内,在表格新增列标记所属多边形,不属于任何多边形则标记为NIL。之前手动在QGIS筛选效率太低,求Excel、QGIS或其他工具的高效方案。
示例
输入
| Latitude | Longitude |
|---|---|
| 19.062892 | 72.882464 |
| 28.630800 | 77.233433 |
输出
| Latitude | Longitude | Polygon |
|---|---|---|
| 19.062892 | 72.882464 | 孟买 |
| 28.630800 | 77.233433 | 德里 |
方法一:QGIS自动化空间连接(最推荐,适合大数据量)
- 加载数据:
- 把Excel坐标表另存为CSV,通过
图层 > 添加图层 > 添加分隔文本图层导入,设置X为Longitude、Y为Latitude,坐标系选WGS84(EPSG:4326)。 - 导入多边形图层(城市边界),确保和点图层坐标系一致。
- 把Excel坐标表另存为CSV,通过
- 空间连接:
- 打开
处理工具箱 > 矢量通用 > 连接属性(按位置)。 - 目标图层选点图层,连接图层选多边形图层;连接类型选
保留所有记录(要保留所有点,包括不在多边形内的)。 - 勾选
目标要素在连接要素内,输出字段选多边形的名称字段(比如城市名)。
- 打开
- 处理结果:
- 右键连接后的图层,选择
导出 > 保存要素为,导出为Excel/CSV格式。 - 把未匹配到多边形的点对应的Polygon列填充为
NIL。
- 右键连接后的图层,选择
方法二:Excel实现(适合小数据量)
方案1:Power Query自定义函数
- 把每个多边形的顶点坐标整理成表格,包含
城市名、纬度、经度列,和点数据一起导入Power Query。 - 新建自定义函数实现射线法判断点是否在多边形内(核心逻辑:统计点向右射线与多边形边的交点数,奇数则在内部),示例函数:
let IsPointInPolygon = (pointLat as number, pointLon as number, polygonPoints as list) as logical => let count = List.Count(polygonPoints), inside = false, Loop = List.Generate( () => [i=0, j=count-1, inside=inside], each [i] < count, each [ i = [i]+1, j = [i]-1, inside = if ( (polygonPoints{[i]}[纬度] > pointLat) <> (polygonPoints{[j]}[纬度] > pointLat) and pointLon < (polygonPoints{[j]}[经度]-polygonPoints{[i]}[经度])*(pointLat-polygonPoints{[i]}[纬度])/(polygonPoints{[j]}[纬度]-polygonPoints{[i]}[纬度])+polygonPoints{[i]}[经度] ) then not [inside] else [inside] ], each [inside] ), Result = List.Last(Loop) in Result in IsPointInPolygon - 对每个点遍历所有多边形,调用函数判断,返回匹配的城市名,无匹配则返回
NIL。
方案2:第三方插件
安装MapTools插件,用自带的POINTINPOLYGON()函数,直接传入点坐标和多边形顶点范围就能得到结果。
方法三:Python脚本(适合技术人员,可批量自动化)
- 先安装依赖库:
pip install pandas geopandas shapely - 编写脚本批量处理:
注:把import pandas as pd import geopandas as gpd from shapely.geometry import Point # 读取点数据 points_df = pd.read_excel("销售线索坐标.xlsx") # 转换为地理数据格式 geometry = [Point(xy) for xy in zip(points_df['Longitude'], points_df['Latitude'])] points_gdf = gpd.GeoDataFrame(points_df, geometry=geometry, crs="EPSG:4326") # 读取多边形数据(支持shp/GeoJSON等格式) polygons_gdf = gpd.read_file("城市边界.shp") polygons_gdf = polygons_gdf.to_crs("EPSG:4326") # 空间匹配 joined_gdf = gpd.sjoin(points_gdf, polygons_gdf, how="left", predicate="within") # 填充无匹配的结果为NIL joined_gdf['Polygon'] = joined_gdf['城市名字段'].fillna('NIL') # 导出到Excel joined_gdf.to_excel("带归属地的销售线索.xlsx", index=False)城市名字段替换成你多边形图层里存储城市名称的字段。
内容的提问来源于stack exchange,提问作者VVstack43
相关产品推荐
相关产品推荐

