Copy selected features to geodatabase feature class

3792
34
Jump to solution
06-11-2015 08:23 AM
Highlighted
Regular Contributor

I am working on creating a addon button to update some address points and copy that updated feature. The first part of the code does what it is suppose to do (only update the selected feature) but the second part of the code doesn't do what it is suppose to do and that is copy "only" the selected feature to the file geodatbase feature class. The code runs fine i don't get any errors but the second part of the codes doesn't copy the selected feature.

I would also like to an an "if" statement. if there is no feature selected i want it to do nothing or tell me there is nothing selected. if there is something selected i want it to only updates the selected feature and only copy the selected feature. Any ideas?

import arcpy, time

import pythonaddins

import os

#populate selected feature

APT = "TEST"

arcpy.env.overwriteOutput = True

mxd = arcpy.mapping.MapDocument("CURRENT")

if int(arcpy.GetCount_management(APT).getOutput(0)) > 0:

    rows = arcpy.UpdateCursor(APT)

    for row in rows:

        row.FacltyType = ("Single Family Home")

        row.StructType = ("Primary, Private")

        row.Verified = ("Yes, GRM, TA")

        row.Status = ("Active")

        row.StructCat = ("Residential")

        row.APA_CODE = ("1110")

        rows.updateRow(row)

    del row, rows

#Copies address point to backup address points in filegeodatabase

fc1 = "CCAP"

#Database

workspace = r"C:\GIS\CCAP\CCAP.mdb"

arcpy.env.overwriteOutput = True

# Start an edit session. Must provide the worksapce.

edit = arcpy.da.Editor(workspace)

# Edit session is started without an undo/redo stack for versioned data

#  (for second argument, use False for unversioned data)

edit.startEditing(True)

# Start an edit operation

edit.startOperation()

if int(arcpy.GetCount_management(APT).getOutput(0)) > 0:

    arcpy.Append_management(APT, fc1, "NO_TEST")

# Stop the edit operation.

edit.stopOperation()

# Stop the edit session and save the changes

edit.stopEditing(True)

arcpy.RefreshActiveView()

Tags (1)
Reply
0 Kudos
1 Solution

Accepted Solutions
Highlighted
MVP Honored Contributor

Yes, lists are the key to what you want to do.  that is why the arcpy.ListFields function returns a list of field objects (not just field names).  With two of these lists from different databases you can create a looping structure that is nearly identical to the code I provided to relate the two lists and perform updates.  The list of field objects can easily be converted to the list of field names used by the cursors.

So here is some code that should work for relating two field lists for two different data sources using the ListFields function.  Since the field lists for both the update cursor and insert cursor match you can use the same row object for the updateRow and InsertRow methods:

import arcpy    

from datetime import datetime as d    

startTime = d.now()    

    

#set to folder where features are located    

arcpy.env.workspace = r"C:\Users\OWNER\Desktop\Test" #on windows use \ instead of /    

arcpy.env.overwriteOutput = True    

#---------------------------    

#define variables for cursor    

#---------------------------    

FC = "test"    

incidentsFC = "CCAP"

FCfields = arcpy.ListFields(FC) 

incidentsFCfields = arcpy.ListFields(incidentsFC) 

# Create a field list of fields you want to manipulate and not just copy 

# All of these fields must be in the incidentsFC 

manualFields =  ["FacltyType", "StructType", "Verified", "Status", "StructCat", "APA_CODE", "ACCOUNT", 'SiteStreet', 'SHAPE@X', 'SHAPE@Y'] 

matchedFields = [] 

for manualField in manualFields: 

    matchedFields.append(manualField.upper()) 

for FCfield in FCfields: 

    for incidentFCfield in incidentsFCfields: 

        # if FCfield.name.upper() == incidentFCfield.name.upper() and \ 

        # FCfield.type == incidentFCfield.type and \ 

        # incidentFCfield.editable() and \ 

        # not FCfield.name.upper() in matchedFields: 

        if FCfield.name.upper() == incidentFCfield.name.upper() and FCfield.type == incidentFCfield.type and incidentFCfield.editable == True and not (FCfield.name.upper() in matchedFields): 

            matchedFields.append(FCfield.name) 

            break 

 

parcelsCount = int(arcpy.GetCount_management(FC).getOutput(0))  

 

dsc = arcpy.Describe(FC)      

 

rowInserter = arcpy.da.InsertCursor(incidentsFC, matchedFields)     

    

selection_set = dsc.FIDSet      

if len(selection_set) == 0:    

    print "There are no features selected"

          

elif parcelsCount >= 1:        

    with arcpy.da.UpdateCursor(FC, matchedFields) as rows:    

        for row in rows:    

            row[0] = ("Single Family Home")        

            row[1] = ("Primary, Private")        

            row[2] = ("Yes, GRM, TA")        

            row[3] = ("Active")        

            row[4] = ("Residential")        

            row[5] = ("1110")    

            rows.updateRow(row)    

      

            rowInserter.insertRow(row)  

    del row    

    del rows    

    del rowInserter

  

arcpy.RefreshActiveView()                          

try:  

    print '(Elapsed time: ' + str(d.now() - startTime)[:-3] + ')'  

  

except Exception, e:  

    # If an error occurred, print line number and error message  

    import traceback, sys  

    tb = sys.exc_info()[2]  

    print "Line %i" % tb.tb_lineno  

    print e.message

View solution in original post

34 Replies
Highlighted
Frequent Contributor

Hey there, it's not necessary to be in an edit session to use the append tool. Try this:

import arcpy

#populate selected feature

APT = "TEST"

fc1 = "CCAP"

workspace = r"C:\GIS\CCAP\CCAP.mdb"

arcpy.env.overwriteOutput = True

mxd = arcpy.mapping.MapDocument("CURRENT")

if int(arcpy.GetCount_management(APT).getOutput(0)) > 0:

    rows = arcpy.UpdateCursor(APT)

    for row in rows:

        row.FacltyType = ("Single Family Home")

        row.StructType = ("Primary, Private")

        row.Verified = ("Yes, GRM, TA")

        row.Status = ("Active")

        row.StructCat = ("Residential")

        row.APA_CODE = ("1110")

        rows.updateRow(row)

        arcpy.Append_management(APT, fc1, "NO_TEST")

        del row, rows

    elif int(arcpy.GetCount_management(APT).getOutput(0)) == 0:

        print "There are no features selected"

    arcpy.RefreshActiveView()

Reply
0 Kudos
Highlighted
Regular Contributor

I am getting an error on elif int(arcpy.GetCount_management(APT).getOutput(0)) == 0

Parsing error SyntaxError: invalid syntax (line 21)

Reply
0 Kudos
Highlighted
Frequent Contributor

Oh yes, I see the mistake. It needs to be indented to the same level as if, and then print statement should be indented level with rows, and refresh view shouldn't be indented.

Reply
0 Kudos
Highlighted
Regular Contributor

after adjusting the indents and when nothing is select and run the code i get the following error on line 18

Runtime error

Traceback (most recent call last):

  File "<string>", line 18, in <module>

NameError: name 'rows' is not defined

import arcpy 

 

#populate selected feature 

APT = "TEST" 

fc1 = "CCAP" 

workspace = r"C:\GIS\CCAP\CCAP.mdb" 

arcpy.env.overwriteOutput = True 

mxd = arcpy.mapping.MapDocument("CURRENT") 

if int(arcpy.GetCount_management(APT).getOutput(0)) > 0: 

    rows = arcpy.UpdateCursor(APT) 

    for row in rows: 

        row.FacltyType = ("Single Family Home") 

        row.StructType = ("Primary, Private") 

        row.Verified = ("Yes, GRM, TA") 

        row.Status = ("Active") 

        row.StructCat = ("Residential") 

        row.APA_CODE = ("1110") 

        rows.updateRow(row) 

        arcpy.Append_management(APT, fc1, "NO_TEST") 

        del row, rows 

elif int(arcpy.GetCount_management(APT).getOutput(0)) == 0: 

    print "There are no features selected" 

With a point selected i don't get any error. The "TEST" point that is selected does the fields updated but nothing is copied to the "CCAP" feature class.

Reply
0 Kudos
Highlighted
MVP Esteemed Contributor

your cursor needs to be outside the​ if statement (into line 8.5) because it is undefined if the count is 0 and goes to the 'else' portion of the if-else

Highlighted
Regular Contributor

interesting i am not sure i follow into line 8.5?

Reply
0 Kudos
Highlighted
MVP Esteemed Contributor

​hmmmmm maybe between line 8 and 9

Highlighted
Regular Contributor

That is what i thought you meant but just making sure.

having nothing selected i still get the error

"Runtime error

Traceback (most recent call last):

  File "<string>", line 18, in <module>

NameError: name 'rows' is not defined"

import arcpy 

 

#populate selected feature 

APT = "TEST" 

fc1 = "CCAP" 

workspace = r"C:\GIS\CCAP\CCAP.mdb" 

arcpy.env.overwriteOutput = True 

mxd = arcpy.mapping.MapDocument("CURRENT")

rows = arcpy.UpdateCursor(APT)

for row in rows:

    if int(arcpy.GetCount_management(APT).getOutput(0)) > 0:           

            row.FacltyType = ("Single Family Home") 

            row.StructType = ("Primary, Private") 

            row.Verified = ("Yes, GRM, TA") 

            row.Status = ("Active") 

            row.StructCat = ("Residential") 

            row.APA_CODE = ("1110") 

            rows.updateRow(row) 

            arcpy.Append_management(APT, fc1, "NO_TEST") 

            del row, rows 

     elif int(arcpy.GetCount_management(APT).getOutput(0)) == 0: 

         print "There are no features selected" 

Am i not doing something correct? Am i going about this the best way?

Reply
0 Kudos
Highlighted
MVP Esteemed Contributor

​well line 20 is not right...rows gets deleted the first time throw the cursor... move that row completely outside of the for row in rows loop or comment it out for testing ie

# del row,rows

Reply
0 Kudos