Select by Location Alternatives

135
4
Jump to solution
02-01-2022 02:36 PM
WillemVan_Riet1
New Contributor II

Hi there, 

I am looking to find out which protected areas (output_PA_clip) fall into a planning unit (spatialjoin_fc), using the Select Layer by Location tool. If they meet this criteria, I would like them populate a field ("lock_out") to be "TRUE"  (this is for a Marxan type model)

Running this through arcpy creates individual "layers" (although not saved to the gdb) for each PU that meets this criteria. With run times of over 4 hours and the creation of 2000 + layers

Is there a way to "select" the feature based on my specific query but not have them create new layers each time?

Code below: 

values = [row[0] for row in arcpy.da.SearchCursor(spatialjoin_fc, "lock_out")]

with arcpy.da.InsertCursor(spatialjoin_fc, "lock_out") as cursor:
    for row in values:
        arcpy.SelectLayerByLocation_management(spatialjoin_fc, "have_their_center_in", output_PA_clip )
        row[0] == 'TRUE'
    cursor.insertRow(row)
del cursor

Thanks for your help!

0 Kudos
1 Solution

Accepted Solutions
JeffK
by MVP Regular Contributor
MVP Regular Contributor

I think that you want an UpdateCursor to change the field value rather than inserting a new feature, which is what the InsertCursor does.

You mention that you want to "find out which protected areas (output_PA_clip) fall into a planning unit (spatialjoin_fc)..."  The way it is in your code, it is backwards. It's saying select if the spatial_join feature has ITS center in the output_PA_clip. You may be missing valid selections and also getting false positives. Do they just have to intersect or do they need to have their center within the planning unit? 

You may be able to get away with only one cursor, iterating over the selected items and updating them to true.

Edit: You also have == in your row[0] assignment that should be one =.

 

selectedFeatures = arcpy.SelectLayerByLocation_management(spatialjoin_fc,  "INTERSECT", output_PA_clip)
with arcpy.da.UpdateCursor(selectedFeatures, ["lock_out"]) as cursor:
    for row in cursor:
        row[0] = 'TRUE'
        cursor.updateRow(row)

 

 

View solution in original post

0 Kudos
4 Replies
DanPatterson
MVP Esteemed Contributor

Not sure but it appears that a select by attributes to get all values would be simplest, then a single select by location which will use the subset of the first step.

select_by_attributes.png

doing it manually,

but once that set is selected all you are doing with the spatial join and assigning all those that meet the spatial condition the same value.


... sort of retired...
0 Kudos
JeffK
by MVP Regular Contributor
MVP Regular Contributor

I think that you want an UpdateCursor to change the field value rather than inserting a new feature, which is what the InsertCursor does.

You mention that you want to "find out which protected areas (output_PA_clip) fall into a planning unit (spatialjoin_fc)..."  The way it is in your code, it is backwards. It's saying select if the spatial_join feature has ITS center in the output_PA_clip. You may be missing valid selections and also getting false positives. Do they just have to intersect or do they need to have their center within the planning unit? 

You may be able to get away with only one cursor, iterating over the selected items and updating them to true.

Edit: You also have == in your row[0] assignment that should be one =.

 

selectedFeatures = arcpy.SelectLayerByLocation_management(spatialjoin_fc,  "INTERSECT", output_PA_clip)
with arcpy.da.UpdateCursor(selectedFeatures, ["lock_out"]) as cursor:
    for row in cursor:
        row[0] = 'TRUE'
        cursor.updateRow(row)

 

 

0 Kudos
WillemVan_Riet1
New Contributor II

Thanks for your prompt and keen attention @JeffK 

Will correct my code and update with my results. 

0 Kudos
WillemVan_Riet1
New Contributor II

Your solutions work - thanks so much @JeffK . Meant to update this months ago!! 

0 Kudos