Search code examples
pythonloopsarcgisarcpy

ArcGIS script is buffering all features each time through the loop -- why?


I have a polygon shapefile with several records. I need to buffer each of those individually and create a new buffered polygon shapefile for each.

I have written the following standalone script in ArcPy. It does some of what i need, but instead of creating a separate buffered polygon shapefile for each record, it creates several shapefiles each with one multipart polygon containing buffers applied to all features. I would like to know how I can change that.

I am using ArcGIS 10.3.1.

import arcpy
from arcpy import env

file_workspace = "C:\\Data\\Temp\\"
env.workspace = file_workspace
arcpy.env.overwriteOutput = True

fc_In1 = file_workspace + "fc_InPolygon.shp"
fc_In1_FieldName = "PLOTNAME"
var_Buffer = "50 Meters"
numCount = 1

# Iterate through the rows in the cursor and buffer each
with arcpy.da.SearchCursor(fc_In1, fc_In1_FieldName) as cursor:
    for row in cursor:
        var_PolygonName = row[0]
        print "Buffering polygon " + var_PolygonName
        arcpy.MakeFeatureLayer_management(fc_In1, "Poly_lyr")
        arcpy.Buffer_analysis("Poly_lyr", var_PolygonName+'_Buff.shp', var_Buffer, "FULL", "ROUND", "ALL", "")

Solution

  • Your script is repeatedly making a layer with all features from the input feature class, and then buffering that layer (hence, multiple output shapefiles all containing the same thing).

    You need to either include a select by attribute, or make your feature layer using a SQL query, to limit what is in the feature layer before it is buffered.

    In either case, your query is along the lines of '"FIELDNAME" = \'POLYGONNAME\'', or, using variables, either:

    • '"{}" = \'{}\''.format(fc_In1_FieldName, var_PolygonName)
    • '"' + fc_In1_FieldName + '" = \'' + var_PolygonName + '\''

    (I like the format method for readability when concatenating, especially when working with that many single/double quotation marks.)

    # Using MAKE FEATURE LAYER with SQL QUERY
    with arcpy.da.SearchCursor(fc_In1, fc_In1_FieldName) as cursor:
        for row in cursor:
            var_PolygonName = row[0]
            print "Buffering polygon " + var_PolygonName
            arcpy.MakeFeatureLayer_management(fc_In1, "Poly_lyr", '"{}" = \'{}\''.format(fc_In1_FieldName, var_PolygonName))
            arcpy.Buffer_analysis("Poly_lyr", var_PolygonName+'_Buff.shp', var_Buffer, "FULL", "ROUND", "ALL", "")
    

    The primary advantage of SelectLayerByAttribute is that you aren't making dozens/hundreds of feature layers in memory, but that may not be a concern for a small feature class.

    # Using SELECT BY ATTRIBUTE
    arcpy.MakeFeatureLayer_management(fc_In1, "Poly_lyr")     # no need to make the layer each time through the cursor
    with arcpy.da.SearchCursor(fc_In1, fc_In1_FieldName) as cursor:
        for row in cursor:
            var_PolygonName = row[0]
            print "Buffering polygon " + var_PolygonName
            arcpy.SelectLayerByAttribute_management("Poly_lyr", "NEW_SELECTION", '"{}" = \'{}\''.format(fc_In1_FieldName, var_PolygonName))
            arcpy.Buffer_analysis("Poly_lyr", var_PolygonName+'_Buff.shp', var_Buffer, "FULL", "ROUND", "ALL", "")