Ottenere l'estensione di ciascun poligono nel file di forma usando ArcPy?


20

In ArcGIS 10 e Python voglio ottenere le informazioni di estensione (xmax, ymax, xmin, ymin) di ciascuno dei poligoni in un file di forma.

Posso ottenere l'estensione dell'intero file di forma usando

file=r"D:\SCRATCH\ARCGIS\100k_trc_tiles_TVM.shp"
desc=arcpy.Describe(file)
print desc.extent.Xmax

394.551,52085039532

Ma non riesco a capire come ottenere le stesse informazioni per ogni riga nel set di dati.

rows = arcpy.SearchCursor("100k_trc_tiles_TVM")
for row in rows:
 print row

stampa le 31 righe nel set di dati ma

for row in rows:
 desc=arcpy.Describe(row)
 print desc.extent.Xmax

dà un errore.

Errore di runtime: Oggetto: descrivere il valore di input non è un tipo valido

Stavo pensando di aggiungere i valori di estensione alla tabella usando "calcola geometria" ma questo dà solo il centroide. Quindi immagino che possiamo usare qualcosa come row.GetValue ("xmax").

Detto questo, so che possiamo creare l'X / Y, max / min usando la funzione di http://www.ian-ko.com/free/free_arcgis.htm, ma sarebbe meglio se possiamo evitare di dover aggiungere campi, specialmente se ArcPy può ottenere questi valori.

Fondamentalmente ho bisogno di ottenere le estensioni da inserire nello strumento di clip per ritagliare 30 aree di dati (secondo i fogli della mappa 1: 100.000) per il geoprocessing poiché lo strumento di divisione non riesce a causa delle grandi dimensioni del set di dati (vedi Perché Intersect fornisce ERRORE 999999: Errore nell'esecuzione della funzione Topologia non valida [Troppi endpoint lineeg]? ). Voglio automatizzare questo come viene ripetuto su una serie di set di dati.

=== script di lavoro ===

# Emulates Arc Info SPLIT tool by using Clip but
# Requires a FC from which each row is used as the input clip feature.
# Each row must be rectangular.
# Used on 12GB FGDB with 100 million records.


#Licence: Creative Commons
#Created by: George Corea; georgec@atgis.com.au, coreagc@gmail.com
import arcpy, string

#inFrame=arcpy.GetParameterAsText(0) # Input dataframe FC
#inFile=arcpy.GetParameterAsText(1) # Input FC for splitting
#outDir=arcpy.GetParameterAsText(2) # Output FGDB

inFrame=r"D:\SCRATCH\ARCGIS\100k_trc_tiles_TVM.shp"
inFile=r"c:\junk\106\data\7_Merge.gdb\FullRez_m2b"
outDir=r"D:\SCRATCH\Projects\206\datasplit\test_slaasp.gdb"
#NameField="Name_1"

#arcpy.env.workspace = r"C:/Workspace"
arcpy.env.overwriteOutput = True

rows = arcpy.SearchCursor(inFrame)
shapeName = arcpy.Describe(inFrame).shapeFieldName
for row in rows:
    feat = row.getValue(shapeName)
    Name = row.Name_1
    print "Executing clip on: "+str(Name)
    extent = feat.extent
    #print extent.XMin,extent.YMin,extent.XMax,extent.YMax
# Create an in_memory polygon
    XMAX = extent.XMax
    XMIN = extent.XMin
    YMAX = extent.YMax
    YMIN = extent.YMin
    pnt1 = arcpy.Point(XMIN, YMIN)
    pnt2 = arcpy.Point(XMIN, YMAX)
    pnt3 = arcpy.Point(XMAX, YMAX)
    pnt4 = arcpy.Point(XMAX, YMIN)
    array = arcpy.Array()
    array.add(pnt1)
    array.add(pnt2)
    array.add(pnt3)
    array.add(pnt4)
    array.add(pnt1)
    polygon = arcpy.Polygon(array)
    ShapeFile = outDir+"\\temp_poly"
    arcpy.CopyFeatures_management(polygon, ShapeFile)

    #print Name
### Set local variables
    in_features = inFile
    clip_features = ShapeFile
    out_feature_class = outDir+"\\"+Name
    xy_tolerance = "0.22"

    # Execute Clip

    try:
        arcpy.Clip_analysis(in_features, clip_features, out_feature_class, xy_tolerance)
        print "Completed: "+str(Name)
    except:
        error = arcpy.GetMessages()
        print "Failed on: "+str(Name)+" due to "+str(error)

2
Non è necessario scrivere la funzione di clip su disco, basta usare il poligono in memoria, ad esempio: poligono = arcpy.Polygon (array) arcpy.Clip_analysis (in_features, poligono, out_feature_class, xy_tolerance)
user2856

tks. Hai idea di come posso esportare la riga in un nuovo file di forma in modo che venga utilizzata, anziché solo l'estensione della riga? Questo in modo che possa gestire anche clip non rettangolari.
GeorgeC,

1
Bene, se vuoi solo tagliare quella funzione, nello stesso script, usa semplicemente l'oggetto funzione. Ancora una volta, non è necessario esportare in file di forma, ad esempio: arcpy.Clip_analysis (in_features, feat, out_feature_class, xy_tolerance)
user2856

Per un file di forma o per ogni poligono in un file di forma? Sembra che tu stia parlando di due cose separate qui.
Rayner,

c'è un solo oggetto poligono nel tuo shapefile? in caso contrario, utilizzare per loop per l'estensione degli oggetti.
Aragona,

Risposte:


26

Prendi l'oggetto forma nel cursore e accedi alla sua proprietà di estensione. Vedi la Guida di ArcGIS Lavorare con la geometria in Python :

shapeName = arcpy.Describe(inFeatures).shapeFieldName
for row in rows:
    feat = row.getValue(shapeName)
    extent = feat.extent
    print extent.XMin,extent.YMin,extent.XMax,extent.YMax

1
Grazie Luca. Questo ha funzionato alla grande. Modificherò la mia domanda per avere il nuovo codice di lavoro se qualcuno vuole usare uno strumento che - Utilizza il set di strumenti Clip in modo iterativo per ritagliare regioni rettangolari di una grande classe di caratteristiche. Emula la funzionalità dello strumento di suddivisione delle informazioni sull'arco senza arresti anomali con set di dati fino a 10 GB di FGDB e 100 milioni di record.
GeorgeC,

Una cosa: ho dovuto codificare il nome della colonna per ottenere l'equivalente di Name = row.Name_1 provando l'attributo name come; NameField = "Name_1"; Nome = row.NameField; oppure Name = row + "." + NameField dove NameField = arcpy.GetParameterAsText (2) e il nome è contenuto nella colonna Name_1. Qualche idea? Nota I; ho usato ";" per indicare una nuova linea.
GeorgeC,

1
capito quanto sopra - row.GetValue (xxx) da gis.stackexchange.com/questions/16586/…
GeorgeC

7

Il set di strumenti Bounding Container fa esattamente quello che vuoi. Se vuoi solo frammenti di codice, esamina le funzioni all'interno degli script, uno si occupa esplicitamente dell'estensione.

MODIFICARE

Dovrei aggiungere che lo script aggiungerà valori a un campo sinistro, destro, superiore e inferiore nel file di output creato che può essere utilizzato per l'elaborazione successiva


Grazie. Lo verificherò. Spero di poter usare il codice all'interno dei miei script / modelli di Python.
GeorgeC

2

Ho appena provato Geometria minima limite (busta) (in Gestione dati) in ArcGIS 10 e sembra fare esattamente lo stesso, per tutti i campi.


1

Un altro modo sarebbe quello di fare un SearchCursor () sul file di forma, quindi puoi usare row.shape.extent:

rows = arcpy.SearchCursor(shapefileName)

for row in rows:
   extent = row.shape.extent
   ...
   ...

1

Come coperto in Estrazione delle coordinate dei vertici poligonali in ArcMap? puoi ottenere i vertici di un poligono e quindi aggiungere le coordinate xey di ciascun vertice come campi nella tabella degli attributi. Ciò ha la limitazione di non associare le coordinate max / min direttamente a ciascun poligono, ma ciò può essere ottenuto in alcuni modi.

Il metodo con cui ho più familiarità è leggere i campi xey nelle liste di Python usando il modulo pyshp , che può quindi essere ordinato per trovare i valori massimo e minimo per ciascun poligono. Pyshp può quindi essere utilizzato per aprire una classe writer per aggiungere nuovi campi ai poligoni originali e scrivere questi valori max e min nel poligono corretto.

Credo che ciò possa essere fatto usando l'arcpy, ma ho avuto molti problemi con la scrittura su shapefile in 9.3 usando il geoprocessore, quindi preferisco il metodo pyshp, tuttavia non sono sicuro che il modulo arcpy abbia risolto questi problemi.


0

Hai provato a scrivere in maiuscolo la "M" in "XMax"? Penso che dovrebbe essere:

print desc.extent.XMax

invece di

print desc.extent.Xmax

secondo la documentazione . Ovviamente questo mi fa chiedere come ha funzionato il tuo primo frammento di codice. Ad ogni modo, provaci!

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.