1

I'm a python beginner.

I`m working with ArcGIS 10.2.2 and IDLE Python 2.7.5

I have two tables, table A (top) and table B.

I need to read the attributes for the A-table fields for the selected record and write the fields and their attributes to all rows of the B table. I need the same attribute information for each row the fields.

enter image description here

I'm working with something like this

 with arcpy.da.UpdateCursor(fc2, field3) as cursor:
 for row in cursor:
 row[0] = 'Q'
 cursor.updateRow(row)
 with arcpy.da.UpdateCursor(fc2, field4) as ucursor:
 with arcpy.da.SearchCursor(fc2, field5) as scursor:
 for srow in scursor:
 sval = srow[0]
 urow = ucursor.next()
 urow[0] = "0" + sval.replace("-", "")
 ucursor.updateRow(urow)
PolyGeo
65.5k29 gold badges115 silver badges349 bronze badges
asked Jan 5, 2016 at 18:12
3
  • Possible duplicate of Getting values from attribute table and inserting another table using ArcPy? Commented Jan 5, 2016 at 18:20
  • Write values based on what? do you need to match values in table b or just create b as a copy of a? Commented Jan 5, 2016 at 18:53
  • I need an exact copy of A table (for the seleted record) for both of B's records. I've comptely read the cursor help docs and they don't have the syntax I need I'm working with something like this but it only works for two tables that have equal numbers of records and fields: Commented Jan 5, 2016 at 19:06

1 Answer 1

3

I have a function I call all the time for doing this, but first, you'll need a common field to join by. From the screenshot, looks like you have a one to many relationship between the fields with several road names ('{DEER HOLLOW WAY}{HUNTERS GLEN WAY}{HUNTERS GLEN WAY}') and those with single field names ('DEER HOLLOW WAY'). You'll want to make a field that you can use to match to the records in the second table. You may want to separate this out to a 1 to 1 relationship in a new table like this:

import os
import arcpy
def flattenTable(table, new_fc, read_field='STNAMES', new_field='JOIN_NAMES'):
 # make a copy of schema
 desc = arcpy.Describe(table)
 where = '{} < 0'.format(arcpy.AddFieldDelimiters(table, desc.OIDFieldName))
 path, name = os.path.split(new_fc)
 arcpy.conversion.FeatureClassToFeatureClass(table, path, name, where)
 # add new field
 fields = ['SHAPE@'] + [f.name for f in arcpy.ListFields(table) if f.type not in ('OID','Geometry')]
 f_index = fields.index(read_field)
 arcpy.management.AddField(new_fc, new_field, 'TEXT', field_length=100)
 # search and insert cursors
 used = []
 with arcpy.da.InsertCursor(new_fc, fields + [new_field]) as irows:
 with arcpy.da.SearchCursor(table, fields) as rows:
 for r in rows:
 st_names = set(filter(None, map(lambda x: x.strip('}'), r[f_index].split('{'))))
 # make overlapping features to flat 1M to 1 to 1 relationship
 for st in st_names:
 if st not in used:
 irows.insertRow(r + (st,))
 used += list(st_names) # supress duplicates
 return new_fc
if __name__ == '__main__':
 table = r'C:\Path\to_your\create_position.shp'
 new_fc = r'C:\Path\to_your\create_position_1to1.shp'
 # change field variables if necessary
 # run it
 flattenTable(table, new_fc) #optional args for field names can be added

And finally, after you have added a common "join_field", you can call this function to add the fields. Be sure to change the variables under the __main__ block appropriately.

import arcpy
import os
FIELD_TYPES = {
 'Date':'DATE',
 'String':'TEXT',
 'Single':'FLOAT',
 'Double':'DOUBLE',
 'SmallInteger':'SHORT',
 'Integer':'LONG',
 'GUID':'GUID',
 'Raster':'RASTER'
 }
def CopyFields(source_table, in_field, join_table, join_key, join_values=[]):
 """
 Copies field(s) from one table to another
 Required:
 source_table -- table in which to add new fields
 in_field -- a field that has common values to a field in the join_table.
 think of this as a "join_field"
 join_table -- table with fields to add to source_table
 join_key -- field to match values of the "in_field"
 join_values -- fields to add to source_table (list)
 """
 def Message(msg):
 print msg
 arcpy.AddMessage(msg)
 # Get Catalog path (for feature layers and table views)
 cat_path = arcpy.Describe(source_table).catalogPath
 # Find out if source table is NULLABLE
 if not os.path.splitext(cat_path)[1] in ['.dbf','.shp']:
 nullable = 'NULLABLE'
 else:
 nullable = 'NON_NULLABLE'
 # Add fields to be copied
 update_fields = []
 join_list = [f for f in arcpy.ListFields(join_table)
 if f.type not in('OID', 'Geometry')]
 for field in join_list:
 ftype = field.type
 name = field.name
 length = field.length
 pres = field.precision
 scale = field.scale
 alias = field.aliasName
 domain = field.domain
 for fldb in join_values:
 if fldb == name:
 arcpy.AddField_management(source_table,name,FIELD_TYPES[ftype], pres, scale, length, alias, nullable, '', domain)
 Message("Added '%s' field to \"%s\"" %(name, os.path.basename(source_table)))
 update_fields.insert(join_values.index(fldb), name.encode('utf-8'))
 # update new fields
 #
 # Create Dictionary
 with arcpy.da.SearchCursor(join_table, [join_key] + join_values) as srows:
 path_dict = {r[0]: r[1:] for r in srows}
 # Update Cursor
 with arcpy.da.UpdateCursor(source_table, [in_field] + update_fields) as urows:
 for row in urows:
 if row[0] in path_dict:
 try:
 row[1:] = path_dict[row[0]]
 urows.updateRow(row)
 except:
 continue
 Message('Fields in "%s" updated successfully' %(os.path.basename(source_table)))
 return update_fields
if __name__ == '__main__':
 target_table = r'C:\Path\to_your\targetTable.shp'
 target_join_field = 'SOME_FIELD' # need to calculate this
 join_table = r'C:\Path\to_your\joinTable.shp'
 join_field = 'SOME_FIELD' # need to calculate this
 add_fields = ['QUADNAME', 'MAPNUM', 'EAM_STATUS', 'EAM_POSITION_ID'] #fields from join table to add
 # run it
 CopyFields(target_table, target_join_field, join_table, join_field, add_fields)
answered Jan 5, 2016 at 19:53
0

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

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

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.