How to find out if the array_index of a fcurve is used I'm currently working on the Animation Nodes and I'm trying to read all fcurves of one object and dynamically set the evaluated values on other objects.

data_path = fCurve.data_path
array_index = fCurve.array_index
value = fCurve.evaluate(frame)
targetObject = some object

# How can I know wether to do this:
exec("targetObject.{} = value".format(data_path))

# or this:
exec("targetObject.{}[{}] = value".format(data_path, array_index))


I have a working version using try and except statements but this isn't really nice. I hoped that fcurve.array_index is -1 if it isn't used but it is 0 by default, so I cannot use it.

Just some extra notes:

Ideally the solution is fast but that isn't absolutely necessary because I can cache the result. Based on the decision wether the property at the data path is subscriptable or not, I dynamically create a setAttribute function so that I don't have to use exec for each execution. I talk about > 10.000 executions per second.

cache = {}

def getSetFunction(object, attribute):
    if attribute in cache: return cache[attribute]

    function = createSetFunction(object, attribute)
    cache[attribute] = function
    return function

def createSetFunction(object, attribute):
    data = {}
    try:
        eval("object.{}[0]".format(attribute))
        exec(setAttributeWithIndex.replace("attribute", attribute), data, data)
        return data["setAttributeWithIndex"]
    except:
        try:
            # when the property is not subscriptable 
            eval("object." + attribute)
            exec(setAttributeWithoutIndex.replace("attribute", attribute), data, data)
            return data["setAttributeWithoutIndex"]
        except: pass
    return None

setAttributeWithIndex = '''
def setAttributeWithIndex(object, index, value):
    object.attribute[index] = value
'''

setAttributeWithoutIndex = '''
def setAttributeWithoutIndex(object, index, value):
    object.attribute = value
'''
I believe you can do this from the bl_rna array_count property.  For instance on the array modifier, count isn't relative_offset_diplace is.

&gt;&gt;&gt; C.object.modifiers['Array'].bl_rna.properties['count'].array_length
0

&gt;&gt;&gt;C.object.modifiers['Array'].bl_rna.properties['relative_offset_displace'].array_length
3


I came across the same prob with searching for drivers and adding to UI sliders, and went for the try-except, which I also try to avoid.