在ArcGIS中应用脚本实现批处理

Zhuotong Nan(南卓铜) [email protected]

ArcGIS 9.2提供了脚本功能,可以方便地实现批处理功能。可用脚本包括JS, VBS和Python。以下示例利用Python实现批处理ASCII grid文件到ESRI Binary grid转换的功能。

问题

ASCII grid由matlab代码生成,存储于 LDAS.data 目录。ASCII grid内容如下:

ncols         32
nrows         32
xllcorner     -88
yllcorner     37.75
cellsize      0.125
NODATA_value  -9999
0.000000    0.000000 …

各ASCII grids命名有以下规律:

nbwi3.[yyyy].[mm].[dd].[hh]h.txt

其中[yyyy]是4位年份,[mm]是月份,[dd]是2位日期,[hh]是24制的小时。比如,nbwi3.2001.07.08.15h.txt等。

生成的ESRI Binary grid有以下命名规律:n[yy][mm][dd][hh],其中[yy]是2位年份,[mm]是月份,[dd]是2位日期,[hh]是24制的小时。如n01070814。注意,ESRI grid的命名和长度是有一定要求限制的,所以我们必须要选择合适的,并能区别数据的命名方式。

我们需要做的是将数百个ASCII grids转换成对应的ESRI binary grids。

实现

脚本编写环境我们这里采用免费的PyDev/Eclipse。Python脚本存储在与LDAS.data并列的src目录下。事实上,可以使用任何文本编辑软件来用脚本,但Eclipse提供很多编程增强功能,如智能提示等。

import arcgisscripting
import os

datadir=os.path.abspath(os.path.join(os.getcwd(),"../LDAS.data"))
#print datadir
children=os.listdir(datadir)

#only ".txt" files
txtfiles=[]
grdnames=[]
for child in children:
    root,ext=os.path.splitext(child)
    if (ext==’.txt’):
        txtfiles.append(child);
        grdname=’n’+root[8:19]
        grdname=grdname.replace(‘.’,”)
        grdnames.append(grdname)
# grid names now ready       

gp=arcgisscripting.create()
gp.workspace=datadir

# begin iteration
for i in range(len(grdnames)):
    gp.ASCIIToRaster(txtfiles[i], grdnames[i], "FLOAT")
    print txtfiles[i]

首先,需要通过import arcgisscripting,将arcgisscripting导入Python。arcgisscripting事实上是位于C:Program Filesarcgisbin目录下的arcgisscripting.dll。如果在运行时,提示找不到arcgisscripting库,则需要配置Python库路径。

库导入成功后,gp=arcgisscripting.create() 创建script对象,此后通过“gp.命令”的方式调用script支持的命令。一般来讲,可以在arcgis command window里使用的命令,都会有对象的script调用方式。比如,

ASCIIToRaster的命令语法是ASCIIToRaster_conversion <in_ascii_file> <out_raster> {INTEGER | FLOAT},对应的脚本语法是ASCIIToRaster_conversion (in_ascii_file, out_raster, data_type)。我们可以在ArcGIS Desktop帮助文档里找到。

此外,gp还有一些专用的script命令,比如ListRasters、GetMessage等,大家可以在ArcGIS Desktop帮助文档查询Geoprocessor object。这些命令对于进行批处理迭代时十分有用。

在以上代码中,与geoprocessor有关的代码有,

gp=arcgisscripting.create()
gp.workspace=datadir
gp.ASCIIToRaster(txtfiles[i], grdnames[i], "FLOAT")

workspace设置了当前的工作目录,相当于在command window里执行 “workspace 目录”。

ASCIIToRaster执行实质的转换工作。如果此处我们需要执行位于ArcGIS扩展模块的命令,则需要在调用命令前,先对扩展模块(如spatial analysis)进行checkout。使用以下命令:

gp.CheckOutExtension("Spatial")
gp.CellStatistics_sa(…)

否则CellStatistic_sa会抱怨说没有License可用。

代码其余部分是常规Python代码。以下取得指定目录下的txt扩展名的全部文件名,并生成对应的grid文件名。

children=os.listdir(datadir)

#only ".txt" files
txtfiles=[]
grdnames=[]
for child in children:
    root,ext=os.path.splitext(child)
    if (ext==’.txt’):
        txtfiles.append(child);
        grdname=’n’+root[8:19]
        grdname=grdname.replace(‘.’,”)
        grdnames.append(grdname)

Python十分有趣,如果有其它语言基础,学习起来并不难。对我们写ArcGIS脚本,有一般的Python知识就足够了。尽管效率不如传统的arcinfo AML高,但在功能上则不逊色。如果需要实现十分复杂的GIS功能,则建议使用c++, vb或.net语言操作ArcObjects。

Leave a Reply

Your email address will not be published.