合并点
对点进行积分,以使彼此之间1 m之内的任何点
成为一个点
创建要素图层,在其中选择z <10的点
缓冲点
多边形到栅格的1m分辨率
重新分类,其中1-9 = 1; NoData = 0
每个shapefile大约有250,000至350,000个点,覆盖〜5x7 km。用作输入的点数据表示树的位置。每个点(即树)具有相关联的“ z”值,该“ z”值表示冠部半径,并且在缓冲过程中使用。我的目的是在单独的过程中使用最终的二进制输出来生成描述遮篷的栅格。
我对四个shapefile进行了测试,结果生成了700MB的栅格,耗时35分钟(i5处理器和8GB RAM)。鉴于我将需要在3500个shapefile上运行此过程,因此,我希望获得任何简化该过程的建议(请参阅随附的代码)。一般来说,处理地理数据的最佳方法是什么?更具体地说,对代码或工作流程是否有任何有助于提高效率的调整?
编辑:
地理处理任务的时间(占总数的百分比):
合并= 7.6%
集成= 7.1%
对Lyr的功能= 0
缓冲区= 8.8%
对栅格的多边形= 74.8%
重新分类= 1.6%
# Import arcpy module
import arcpy
# Check out any necessary licenses
arcpy.CheckOutExtension("spatial")
# Script arguments
temp4 = arcpy.GetParameterAsText(0)
if temp4 == '#' or not temp4:
temp4 = "C:\gdrive\temp\temp4" # provide a default value if unspecified
Reclassification = arcpy.GetParameterAsText(1)
if Reclassification == '#' or not Reclassification:
Reclassification = "1 9 1;NODATA 0" # provide a default value if unspecified
Multiple_Value = arcpy.GetParameterAsText(2)
if Multiple_Value == '#' or not Multiple_Value:
Multiple_Value = "C:\t1.shp;C:\t2.shp;C:\t3.shp;C:\t4.shp" # provide a default value if unspecified
# Local variables:
temp_shp = Multiple_Value
Output_Features = temp_shp
temp2_Layer = Output_Features
temp_Buffer = temp2_Layer
temp3 = temp_Buffer
# Process: Merge
arcpy.Merge_management(Multiple_Value, temp_shp, "x \"x\" true true false 19 Double 0 0 ,First,#,C:\#########omitted to save space
# Process: Integrate
arcpy.Integrate_management("C:\gdrive\temp\temp.shp #", "1 Meters")
# Process: Make Feature Layer
arcpy.MakeFeatureLayer_management(temp_shp, temp2_Layer, "z <10", "", "x x VISIBLE NONE;y y VISIBLE NONE;z z VISIBLE NONE;Buffer Buffer VISIBLE NONE")
# Process: Buffer
arcpy.Buffer_analysis(temp2_Layer, temp_Buffer, "z", "FULL", "ROUND", "NONE", "")
# Process: Polygon to Raster
arcpy.PolygonToRaster_conversion(temp_Buffer, "BUFF_DIST", temp3, "CELL_CENTER", "NONE", "1")
# Process: Reclassify
arcpy.gp.Reclassify_sa(temp3, "Value", Reclassification, temp4, "DATA")
#1 楼
可以对您有所帮助的一些算法更改。在合并或集成之前先执行选择。这将大大减少以后最昂贵的功能。
合并和集成都占用大量内存,因此您希望在引入要素类时不断消除要素,并尝试进行合并在二叉树中保留合并和集成的大小。例如对于四个shapefile,可以合并两个shapefile并进行集成;合并另外两个shapefile并进行整合;合并两个结果要素类并进行集成。
您的作业队列从shapefile引用队列开始。您还可以将结果队列放入结果中。
并行处理工作程序的run()方法将执行以下操作:
从队列中取出两个项目。如果没有任何物品(队列为空),请终止该工作程序。如果采用一项,则将其直接放入结果队列。
如果采用两项,则对每一项:如果是shapefile,则选择z <10并创建一个in_memory要素类;否则,它已经是in_memory要素类,并跳过选择步骤。合并两个in_memory要素类以创建一个新的in_memory要素类。删除原始的两个要素类。对新要素类执行集成。将要素类放入结果队列。
然后运行外部while循环。循环从shapefile队列开始,并测试其长度是否大于1。然后,循环通过工作程序运行队列。如果结果队列的长度大于1,则while循环将通过工作程序执行另一个并行处理,直到结果队列为1个in_memory要素类。
例如如果以3500个shapefile开头,则第一个队列将有3500个作业。第二名将有1750个工作岗位。 875、438、219、110、55、28、14、7、4、2、1。最大的瓶颈将是记忆。如果您没有足够的内存(如果是这种情况,那么您将在创建第一个结果队列时耗尽内存),然后修改算法以一次合并两个以上的要素类,然后进行集成,这将减少第一个结果队列的大小,以换取更长的处理时间。
或者,您可以编写输出文件,并使用in_memory要素类跳过。这将大大降低您的速度,但会克服内存瓶颈。
仅在对所有shapefile执行合并和集成之后,以一个要素类结束,然后才执行缓冲区,多边形以栅格化并重新分类。这样,这三个操作仅执行一次,即可保持几何简单。
评论
如果您的数据适合内存,则使用+1以使用in_memory工作空间。它大大加快了地理处理的速度。
– RyanKDalton
2012年8月7日在22:23
这是好东西。我认为使用图表和一些伪代码(或真实代码!)可能会更好。
–blah238
2012年8月9日在21:40
是的,我希望我有一些时间致力于编写代码。无论如何,我都需要编写一个新的并行处理演示脚本。
– Blord-castillo
2012年8月10日,0:09
#2 楼
我要做的第一件事是使用Windows 7中的Resource Monitor或Vista / XP中的perfmon之类的工具监视系统的资源利用率,以了解是否受CPU,内存或IO限制。如果内存或IO受限,那么您几乎无能为力,只能升级硬件,减小问题大小或完全改变方法。
如果确定自己是CPU-必然,我将尝试使用
multiprocessing
模块或可用的其他许多基于Python的并行处理程序包之一,以查看是否可以使用更多的CPU内核来加快操作速度。通常,多处理和并行性正在寻找一种很好的分区方案: />增加了最少的开销(与串行处理相比是不可避免的),
允许您调整工作区的大小rking可以最佳利用系统资源以获得最佳性能。
您可以将我在此答案中创建的脚本用作起点:将用于生成建筑阴影的Avenue代码移植到ArcPy / Python for ArcGIS Desktop?
另请参阅ESRI地理处理博客文章,主题:
Python多重处理–方法和注意事项
由于您的情况,我认为您的案件将更具挑战性归因于您所使用的工具更具“黑匣子”性质,而不是我正在使用的更细粒度的几何数组。也许使用NumPy数组可能会派上用场。
如果您想超越arcpy,我也遇到了一些有趣的阅读材料:
GIS的并行处理算法。 CRC出版社,1997年。Richard Healey,Steve Dowers,Bruce Gittings,Mike J Mineter
用细粗粮加速栅格处理
GRASS中的并行性。 2004年FOSS / GRASS用户会议的论文集-泰国曼谷,2004年9月12日至14日。Onil Nazra Persada,Thierry Goubier。
使用GPU加速空间栅格分析的批处理。计算机与地球科学,第45卷,2012年8月,第212–220页。玛蒂亚丝·斯坦巴赫(Reshard Hemmerling)
评论
可能需要输入一些性能计时代码来确定大部分时间是进入一个步骤还是几个步骤-以便可以集中精力尝试并发现性能提升如果您继续使用ArcPy,我认为您没有太多选择可以提高性能。也许您可以看看其他工具来做到这一点? FME之类的工具还是Postgis?
目前尚不清楚使用的是哪种像素类型,但是如果它是“字节”(应该是),那么每个栅格的原始数据存储将为5000x7000 = 35Mb(〜33.4MB),实际上并不是那么大。但是,下一个维度3500(时间维度?)会将原始总大小增加到〜114GB。
尽管我无法从该描述中看出算法在做什么(或打算做什么),但是在大多数情况下,点缓存和随后的栅格化应替换为点的栅格化,再进行焦点统计(通常是均值或总和)。结果将是相同的,但是,通过避免冗长的缓冲和多边形栅格化步骤,可以更快地获得结果。我(强烈)怀疑可以大大提高速度,但由于程序描述的含糊性,无法提供具体建议。
点周围的缓冲区大小可变(基于点的z值)。我想仍然进行焦点统计,您必须将结果点按z值向上分割,并对每组进行栅格和焦点统计(使用z作为最大邻域上的圆形邻域的半径)。然后使用最大统计值对所有9个栅格运行像元统计,以便将结果组合在一起。 (这可能仍比使用大数据集缓冲和栅格化要快得多。)