Update Cursor.

3917
8
10-30-2015 02:57 AM
RajP
by
New Contributor

Hello,

Can any one suggest me to the following code is correct or not?

Note: I need to update GISID from HT_GISID.

Code:

workspace1 = r"D:\ADC\Tool\Mumbai\PGDB For Reference\MVVNL_MAHMUDABAD\MVVNL_MAHMUDABAD.mdb"
workspace2 = r"D:\ADC\Tool\Mumbai\PGDB For Reference\MVVNL_MAHMUDABAD\Output.mdb"

searchFeatures = os.path.join(workspace2, "LTOVerHead_DTGISID")
updateFeatures = os.path.join(workspace1, "SecOHElectricLineSegment")

with arcpy.da.UpdateCursor(updateFeatures, ["OBJECTID", "GISID"]) as cursor1:
    for row1 in cursor1:
        gisiddict={}
        with arcpy.da.SearchCursor(searchFeatures, ["TARGET_FID", "HT_GISID"]) as cursor:
            for row in cursor:
                gisiddict[row[0]] = row[1]
            del row, cursor
        oid = row1[0]
        if(gisiddict.has_key(oid)):
            row1[1] = gisiddict[oid]
        cursor1.updateRow(row1)
    del row1, cursor1

Regards,

Raj P

Message was edited by: Dan Patterson Syntax Highlighting add to make code readable. Tags added to make it useful for searches

0 Kudos
8 Replies
DanPatterson_Retired
MVP Emeritus

Can you post the results showing the inputs and the outputs?

0 Kudos
RajP
by
New Contributor

Hello,

Thanks for replying:

My Inputs are:

Table1:

     

OBJECTID *Shape *TARGET_FID *FeederIDHT GIS IDHT_T CodeSHAPE_Length
2814Polyline156480833232210034TO103003405A8613NA0.518247
2878Polyline156758733232210034SDR03003405A8612NA0.499987
2287Polyline156953233232210034SDR03003405A8610NA28.59185
171Polyline156760933232210034SDR03003405A8610NA0.50004
2288Polyline156953333232210034SDR03003405A8610NA58.23881
780Polyline156376133232210034SDR03003405A8609NA0.282843
2295Polyline156953533232210034SDR03003405A8606NA0.5255
113Polyline156760833232210034TO203003405A8602NA0.500025
37Polyline156953433232210034TO203003405A8601NA0.499996
2877Polyline156758633232210034TO203003405A8600NA0.500021

Table2:

       

OBJECTID *FeederIDGis IDSurvey Building IDSubstation CodeDTRGISID *SHAPE_Length
156480833232210034TO10NOTAP3.32E+103003405A86130.518247
156480733232210034TO20NOTAP3.32E+103003405280.068149
156480633232210034TO20NOTAP3.32E+103003405280.043821
156480533232210034TO20NOTAP3.32E+1030034053150.01936
156480433232210034TO50NOTAP3.32E+1030034055341.90007
156480333232210034TO50NOTAP3.32E+1030034055330.91885
156480233232210034TO50NOTAP3.32E+1030034055336.66272
156480133232210034TO50NOTAP3.32E+1030034055344.50375
156480033232210034TO50NOTAP3.32E+1030034055354.88846
156479933232210034SDR0NOTAP3.32E+103003405482.978194

I tried to update Table2 "GIS ID" from Table1 "HT GIS ID" using Common field
from Table1 as "Target_FID" and Table 2 as "ObjectID"

Regards,

Raj P

0 Kudos
JoshuaBixby
MVP Esteemed Contributor

The first change I would make is to pull your search cursor out of your update cursor.  The current code is creating a new search cursor for every record in the update table, and the same dictionary is being created over and over again.

Give this a try:

workspace1 = r"D:\ADC\Tool\Mumbai\PGDB For Reference\MVVNL_MAHMUDABAD\MVVNL_MAHMUDABAD.mdb"  
workspace2 = r"D:\ADC\Tool\Mumbai\PGDB For Reference\MVVNL_MAHMUDABAD\Output.mdb"  

searchFeatures = os.path.join(workspace2, "LTOVerHead_DTGISID")  
updateFeatures = os.path.join(workspace1, "SecOHElectricLineSegment") 

with arcpy.da.SearchCursor(searchFeatures, ["TARGET_FID", "HT_GISID"]) as cursor:
    gisiddict={} 
    for fid, gisid in cursor:  
        gisiddict[fid] = gisid  
del gisid, fid, cursor

with arcpy.da.UpdateCursor(updateFeatures, ["OBJECTID", "GISID"]) as cursor:  
    for oid, gisid in cursor:    
        if oid in gisiddict:
            cursor.updateRow([oid, gisiddict[oid]])
del gisid, oid, cursor
curtvprice
MVP Esteemed Contributor

Just to mention, as I keep seeing people unnecessarily using del when Python takes care of this on its own...

No need to "del cursor" -- that variable is deleted the cursor is closed, and the table file lock is released when you leave the with block. That's kind of the point of the with block, to delete the variable/close the cursor no matter what happens on exiting the block.

The variables gisid, fid, also don't need to be deleted as they aren't attached to an object (like or layer or cursor would be) and are auto-deleted by python garbage collection when the script ends.

UPDATE: Thank you Joshua Bixby​ I stand corrected. See strikethrough and bold above.

JoshuaBixby
MVP Esteemed Contributor

Python 2.7.10 documentation > 7. Compound Statements > 7.5. The with statement:

The with statement is used to wrap the execution of a block with methods defined by a context manager (see section With Statement Context Managers). This allows common try...except...finally usage patterns to be encapsulated for convenient reuse.

The with statement encapsulates code, but it encapsulates specific types of code within a class.  For someone using a class and not developing one, the with statement is more about wrapping code within a context manager.

The variables defined within a with statement, including the target variable of the with statement, are wrapped and persist after the with statement:

>>> with arcpy.da.SearchCursor(r'Default.gdb\StateProvinceBoundaries_ESRI',"OID@") as cur:
...    for row in cur:
...        pass
...       
>>> dir()
['__builtins__', '__doc__', '__file__', '__name__', '__package__', 'arcgis', 'arcpy', 'cur', 'datetime', 'math', 'row', 'sys', 'time']
>>> type(cur)
<type 'da.SearchCursor'>
>>> type(row)
<type 'tuple'>

The with statement doesn't delete variables and the variables don't go out of scope after the with statement.  For this specific case, the with statement ensures the arcpy.da.SearchCursor.__enter__() and arcpy.da.SearchCursor.__exit__() methods are called, thus freeing some of the locks the cursor holds on the data source.

Regardless of whether a with statement is used or not, the variables will all be cleaned up when the script ends.

DanPatterson_Retired
MVP Emeritus

They really have to work on their help topics arcpy.da.SearchCursor.__enter__() so secretive

0 Kudos
JoshuaBixby
MVP Esteemed Contributor

Dan Patterson​, given how much you like NumPy (who can blame you, it is pretty slick), you might also have fun with arcpy.da.SearchCursor._dtype and arcpy.da.SearchCursor._as_narray().

>>> cur = arcpy.da.SearchCursor(r'StateProvinceBoundaries_ESRI',
                                ["OID@", "SHAPE@XY"],
                                where_clause="NAME1 = 'Minnesota'")
>>> cur._dtype
dtype([('OID@', '<i4'), ('SHAPE@XY', '<f8', (2,))])
>>> cur._as_narray()
array([(139, [205923.5657559298, 5264242.273746617]),
       (140, [544608.9951297314, 5365824.304238412]),
       (141, [221359.03653639136, 4966096.278488112]),
       (142, [580541.5304663723, 5054285.671024574])], 
      dtype=[('OID@', '<i4'), ('SHAPE@XY', '<f8', (2,))])
>>>
>>> help(arcpy.da.SearchCursor._as_narray)
Help on method_descriptor:
_as_narray(...)
    _as_narray() -> numpy.record.
    Return snapshot of the current state as NumPy array.

That part of the API might not be published but Python is for consenting adults.

DanPatterson_Retired
MVP Emeritus

Nicccceee so much for relaxing... have several more things to check... the pesky _method and _property etc things

>>> import arcpy
>>> src = r"F:\Testing\AOI_mtm9.shp"
>>> arcpy.env.workspace = "in_memory"
>>> #
>>> #cur = arcpy.da.SearchCursor(src, *, where_clause=None, spatial_reference) 
>>> SR = arcpy.Describe(src).spatialReference
>>> SR.name
'NAD_1983_CSRS_MTM_9'
>>> 
>>> #-----------------------
>>> # fun time
>>> cur = arcpy.da.SearchCursor(src, "*", where_clause=None, spatial_reference=SR, explode_to_points=True)
>>> cur._dtype
dtype([('FID', '<i4'), ('Shape', '<f8', (2,)), ('Id', '<i4'), ('X_c', '<f8'), ('Y_c', '<f8'), ('area', '<f8')])
>>> cur.fields
('FID', 'Shape', 'Id', 'X_c', 'Y_c', 'area')
>>> a = cur._as_narray()
>>> a
array([(0, [340000.0, 5022000.0], 0, 342000.0, 5024000.0, 16000000.0),
       (0, [340000.0, 5026000.0], 0, 342000.0, 5024000.0, 16000000.0),
       (0, [344000.0, 5026000.0], 0, 342000.0, 5024000.0, 16000000.0),
       (0, [344000.0, 5022000.0], 0, 342000.0, 5024000.0, 16000000.0),
       (0, [340000.0, 5022000.0], 0, 342000.0, 5024000.0, 16000000.0)], 
      dtype=[('FID', '<i4'), ('Shape', '<f8', (2,)), ('Id', '<i4'), ('X_c', '<f8'), ('Y_c', '<f8'), ('area', '<f8')])
>>> import numpy as np
>>> a_clone = a.copy()
>>> a_clone = a_clone.view(type=np.recarray)
>>> a_clone.Shape
array([[  340000.,  5022000.],
       [  340000.,  5026000.],
       [  344000.,  5026000.],
       [  344000.,  5022000.],
       [  340000.,  5022000.]])
>>> a_clone.Shape[1:].mean(axis=0) # skip the duplicate point
array([  342000.,  5024000.])
>>> # oooooo nice!
‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍

hmmmm... me thinks the hole hasn't been dug deep enought... thanks Joshua Bixby

Visit the future.... returned to this topic