1

Regarding the field calculator in the ArcGIS Pro 2.9 attribute table (Python):

Is there a way to skip calculating a certain record, if certain conditions are met in the script?

For example, if the line doesn't have true curves, then calculate the shape normally. But if the line does have true curves, then skip the field calculation — without editing the row/invoking editor tracking.


I can do something that's close to that. I can return the original value. That works, but it does update the row, which seems unnecessary and invokes editor tracking (which is misleading, since nothing's really changed).

return orig_geom

Alternatively, I've tried return without specifying anything to return. But that sets the shape to null, which isn't what I want.

return

The same thing happens if I omit the return entirely. The shape gets set to null.

I know it would be ideal if I could avoid selecting lines with curves in the first place (in the Attribute Table). But I don't think there's a way to query for curves using SQL in the Select By Attributes tool. So doing it in the field calculator script seems like the only other option.


Related ArcGIS Pro Idea: Conditionally skip field calculation for certain rows

2
  • 3
    return, return None, and omitting any return are all equivalent in Python, so that behavior makes sense. Have you tried using an UpdateCursor instead? You could omit updateRow() as necessary
    – mikewatt
    Commented Mar 1, 2022 at 17:42
  • 2
    If you use Field Calculator, it will update all rows (or all selected rows). So you have three options: Alter the selection (you've already ruled this out), put up with editor tracking updates (you've already ruled this out), DON'T use Field Calculator. Instead of Field Calculator, you can, use an arcpy script with an arcpy.da.UpdateCursor(). You can use a where cause to skip rows when the cursor is established, OR you can simply not update a row, one-at-a-time (while iterating through them), as it suits your requirements. Commented Mar 1, 2022 at 21:43

1 Answer 1

1

I don't believe there's a way to skip a record, other than returning a value that cannot be casted to the field's data type. For example if you're calculating a Double field, you can give it the value "A" if you want to skip it, and you'll get some warning like "could not write value 'A' to output field {my_double_field}" for every single feature that gets skipped.

That's obviously super janky and ugly and can give unexpected results since the tool tries pretty hard to cast data types for you. But that doesn't trigger the editor tracking so technically answers your question.

Using arcpy.da.UpdateCursor() is the cleanest alternative. For your example of only editing polyline features with curves:

with arcpy.da.UpdateCursor(in_table, "SHAPE@") as cursor:
    for row in cursor:
        geom = row[0]

        if geom and geom.hasCurves:
            cursor.updateRow(...)

But there are edge cases where that's not possible, for example if your input table has joins. If UpdateCursor is not an option but SearchCursor is (as for a joined table), you could first do a search cursor to find all the features you want to update, then select them and do calculate field. For example:

oids_to_update = []

with arcpy.da.SearchCursor(in_table, ["OID@", "SHAPE@"]) as cursor:
    for row in cursor:
        oid, geom = row

        if geom and geom.hasCurves:
            oids_to_update.append(oid)

oid_str = ",".join([str(o) for o in oids_to_update])
where = f"OBJECTID IN ({oid_str})"
selection = arcpy.management.SelectLayerByAttribute(in_table, "NEW_SELECTION", where)

arcpy.management.CalculateField(selection, ...)
1

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

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