3

I have written a python script tool wherein a user specifies a feature class (e.g., Landuse) containing different attributes (e.g., parcel size, landcover etc.), name of the attribute field from which features will be selected (e.g., "landcover") and the name of the attribute to be selected (e.g., "forest" or "buildings"). The end result should be that the script selects all the features with the specified attribute and create a new feature class out of it. For this I have 3 input parameters, as shown below, and the script receives the input with GetParameterAsText().

Parameters

My code block looks like follows:

FClass = arcpy.GetParameterAsText(0) 
Field = arcpy.GetParameterAsText(1) 
Feature = arcpy.GetParameterAsText(2)

arcpy.MakeFeatureLayer_management(FClass, "FclassLayer")
arcpy.SelectLayerByAttribute_management("FclassLayer","NEW_SELECTION","'Field' = 'Feature'")

arcpy.CopyFeatures_management("FclassLayer", "Feature1.shp")

When I run the script tool, it doesn't produce any error message and creates Feature1.shp, but the shapefile is simply a copy of the specified feature class. That means, SelectLayerByAttribute is simply selecting the whole feature class irrespective of the specified attribute.

Being a beginner with python scripting, I am not being able to locate what am I doing wrong here. Furthermore, I tested the same script with hard coded values instead of getting it from user with GetParameterAsText, and there it runs perfectly and gets me the output as expected.

4

The problem lies in your SelectLayerByAttribute line.

Your query "'Field' = 'Feature'" indicates that you want to select all features in which attribute Field contains the string Feature. This ends up selecting nothing (presumably no fields are named Field and/or contain 'Feature'), and so the CopyFeatures step copies everything in the feature layer.

Since you want those to be treated as variables, try instead:

"{} = '{}'".format(Field, Feature)      # if querying a GDB
'"{}" = \'{}\''.format(Field, Feature)  # if querying a shapefile

That will substitute the user-supplied parameters into the string, and should correctly query, select, and copy.

(If you want to get fancy and always guarantee you have the correct field delimiters regardless of data source, check out this answer.)

2

You have an error here:

arcpy.SelectLayerByAttribute_management("FclassLayer","NEW_SELECTION","'Field' = 'Feature'")

There is no simple quote for fields but 3 others solution explained in doc here

In addition if you want use your variables in query, you need format your query and pass values with format() function detailled in PEP 0498 -- Literal String Interpolation

If your query is on Shapefile, use double quote and enclosed with """ """

arcpy.SelectLayerByAttribute_management(
    "FclassLayer", "NEW_SELECTION", """"{}" = '{}'""".format(Field, Feature))

If your query is on GDB, there is no quote

arcpy.SelectLayerByAttribute_management(
    "FclassLayer","NEW_SELECTION","{} = '{}'".format(Field,Feature))

If your query is on MDB, there is no quote but [ ]

arcpy.SelectLayerByAttribute_management(
    "FclassLayer","NEW_SELECTION","[{}] = '{}'".format(Field,Feature))
  • note : '"{}" = \'{}\'' is equivalent to """"{}" = '{}'""" – GeoStoneMarten Dec 14 '15 at 13:08
1

Firstly if field exists in featureclass which is must, why not set up the parameter (attribute field) to be obtained from the featureclass then a nice drop down appears, currently you are accepting a free-form text so people could potentially enter the wrong field name.

The problem with the code is the expression, you have put the variable Field which holds the field name within a string so the code is looking for a field called Field!

You would need to create an expression something like :

'"' + Field + " = '" + Feature + "'" + '"'

This would change depending upon the format of the source data. Of cause the smart way of resolving this and making your code robust is to call the function AddFieldDelimiters. Search desktop help about this arcpy function.

1

What eventually solved my problem is the following:

arcpy.SelectLayerByAttribute_management("FclassLayer","NEW_SELECTION", """"{}" = '{}'""".format(Field,Feature))

Regarding what if a user inputs a wrong attribute or a wrong field name, for this purpose I have managed to write a validation script to update parameters automatically once a user chooses a feature class. So, when a user chooses a feature class, the field names contained in the feature class appears as a drop down list in the field name input field of the tool and the unique values of parameters for the chosen field appears as a drop down list in the parameter field of the tool.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.