Components

Overview

Component is the base class for all of the objects used to create Compositions in PsyNeuLink. It defines a common set of attributes possessed, and methods used by all Component objects.

Creating a Component

A Component is never created by calling the constructor for the Component base class. However, its __init__() method is always called when a Component subclass is instantiated; that, in turn, calls a standard set of methods (listed below) as part of the initialization procedure. Every Component has a core set of configurable parameters that can be specified in the arguments of the constructor, as well as additional parameters and attributes that may be specific to particular Components, many of which can be modified by the user, and some of which provide useful information about the Component (see User-modifiable Parameters and Informational Attributes below).

Deferred Initialization

If information necessary to complete initialization is not specified in the constructor (e.g, the owner for a State, or the sender or receiver for a Projection), then its full initialization is deferred until its the information is available (e.g., the State is assigned to a Mechanism, or a Projection is assigned its sender and receiver). This allows Components to be created before all of the information they require is available (e.g., at the beginning of a script). However, for the Component to be operational, initialization must be completed its deferred_init method must be called. This is usually done automatically when the Component is assigned to another Component to which it belongs (e.g., assigning a State to a Mechanism) or to a Composition (e.g., a Projection to the pathway) of a Process), as appropriate.

Component Structure

Core Structural Attributes

Every Component has the following set of core structural attributes. These attributes are not meant to be changed by the user once the component is constructed, with the one exception of prefs.

  • variable - used as the input to its function. Specification of the default_variable argument in the constructor for a Component determines both its format (e.g., whether its value is numeric, its dimensionality and shape if it is an array, etc.) as well as its default value (the value used when the Component is executed and no input is provided), and takes precedence over the specification of size.

    Note

    Internally, the attribute variable is not directly used as input to functions, to allow for parallelization. The attribute is maintained as a way for the user to monitor variable along the execution chain. During parallelization however, the attribute may not accurately represent the most current value of variable being used, due to asynchrony inherent to parallelization.

  • size - the dimension of the variable attribute. The size argument of the constructor for a Component can be used as a convenient method for specifying the variable, attribute in which case it will be assigned as an array of zeros of the specified size. For example, setting size = 3 is equivalent to setting variable = [0, 0, 0] and setting size = [4, 3] is equivalent to setting variable = [[0, 0, 0, 0], [0, 0, 0]].
  • function - determines the computation that a Component carries out. It is always the function method of a PsyNeuLink Function object (itself a PsyNeuLink Component).

    Note

    The function of a Component can be assigned either a Functions object or any other callable object in python. If the latter is assigned, it is “wrapped” in a UserDefinedFunction.

    All Components have a default function (with a default set of parameters), that is used if it is not otherwise specified. The function can be specified in the function argument of the constructor for the Component, using one of the following:

    • class - this must be a subclass of Function, as in the following example:

      my_component = SomeComponent(function=SomeFunction)
      

      This will create a default instance of the specified subclass, using default values for its parameters.


    • Function - this can be either an existing Function object or the constructor for one, as in the following examples:

      my_component = SomeComponent(function=SomeFunction)
      
      or
      
      some_function = SomeFunction(some_param=1)
      my_component = SomeComponent(some_function)
      

      The specified Function will be used as a template to create a new Function object that is assigned to the function_object attribute of the Component, the function of which will be assigned as the function attribute of the Component.

      Note

      In the current implementation of PsyNeuLink, if a Function object (or the constructor for one) is used to specify the function attribute of a Component, the Function object specified (or created) is used to determine attributes of the Function object created for and assigned to the Component, but is not itself assigned to the Component. This is so that Functions can be used as templates for more than one Component, without being assigned simultaneously to multiple Components.

    A function can also be specified in an entry of a parameter specification dictionary assigned to the params argument of the constructor for the Component, with the keyword FUNCTION as its key, and one of the specifications above as its value, as in the following example:

    my_component = SomeComponent(params={FUNCTION:SomeFunction(some_param=1)})
    
  • value - the value attribute contains the result (return value) of the Component’s function after the function is called.
  • log - the log attribute contains the Component’s Log, that can be used to record its value, as well as that of Components that belong to it, during initialization, validation, execution and learning. It also has four convenience methods – loggable_items, set_log_conditions, log_values and logged_items – that provide access to the corresponding methods of its Log, used to identify, configure and track items for logging.
  • name - the name attribute contains the name assigned to the Component when it was created. If it was not specified, a default is assigned by the registry for subclass (see Registry for conventions used in assigning default names and handling of duplicate names).
  • prefs - the prefs attribute contains the PreferenceSet assigned to the Component when it was created. If it was not specified, a default is assigned using classPreferences defined in __init__.py Each individual preference is accessible as an attribute of the Component, the name of which is the name of the preference (see PreferenceSet for details).
  • reinitialize_when - the reinitialize_when attribute contains a Condition. When this condition is satisfied, the Component calls its reinitialize method. The reinitialize method is executed without arguments, meaning that the relevant function’s initializer attribute (or equivalent – initialization attributes vary among functions) is used for reinitialization. Keep in mind that the reinitialize method and reinitialize_when attribute only exist on stateful Mechanisms.

    Note

    Currently, only Mechanisms reinitialize when their reinitialize_when Conditions are satisfied. Other types of Components do not reinitialize.

User-modifiable Parameters

  • user_params - a dictionary that provides reference to all of the user-modifiable parameters of a Component. The dictionary is a ReadOnlyDict (a PsyNeuLink-defined subclass of the Python class UserDict). The value of an entry can be accessed in the standard manner (e.g., my_component.user_params[`PARAMETER NAME`]); as can its full list of entries (e.g., my_component.user_params). However, because it is read-only, it cannot be used to make assignments. Rather, changes to the value of a parameter must be made by assigning a value to the attribute for that parameter directly (e.g., my_component.my_parameter), but using a dedicated method if one exists (e.g., Mechanism_Base.add_states), or by using the Component’s assign_params method.

    All of the parameters listed in the user_params dictionary can be modified by the user (as described above). Some can also be modified by ControlSignals when a System executes. In general, only parameters that take numerical values and/or do not affect the structure, mode of operation, or format of the values associated with a Component can be subject to modulation. For example, for a TransferMechanism, clip, initial_value, integrator_mode, input_states, output_states, and function, are all listed in user_params, and are user-modifiable, but are not subject to modulation; whereas noise and integration_rate, as well as the parameters of the TransferMechanism’s function (listed in the function_params subdictionary) can all be subject to modulation. Parameters that are subject to modulation are associated with a ParameterState to which the ControlSignals can project (by way of a ControlProjection).

  • function_object - the function_object attribute refers to the PsyNeuLink Function assigned to the Component; The Function’s function – its callable method – is assigned to the function attribute of the Component. The parameters of the Function can be modified by assigning values to the attributes corresponding to those parameters (see function_params below).
  • function_params - the function_params attribute contains a dictionary of the parameters for the Component’s function and their values. Each entry is the name of a parameter, and its value is the value of that parameter. The dictionary uses a ReadOnlyDict (a PsyNeuLink-defined subclass of the Python class UserList). The value of an entry can be accessed in the standard manner (e.g., my_component.function_params[`PARAMETER NAME`]); as can its full list of its entries (e.g., my_component.function_params). However, because it is read-only, it cannot be used to make assignments. Rather, changes to the value of a function’s parameters must be made by assigning a value to the corresponding attribute of the Component’s function_object attribute (e.g., my_component.function_object.my_parameter), or in a FUNCTION_PARAMS dict using its assign_params method. The parameters for a function can be specified when the Component is created in one of the following ways:

    • in the constructor for a Function – if that is used to specify the function argument, as in the following example:

      my_component = SomeComponent(function=SomeFunction(some_param=1, some_param=2)
      
    • in an argument of the Component’s constructor – if all of the allowable functions for a Component’s function share some or all of their parameters in common, the shared paramters may appear as arguments in the constructor of the Component itself, which can be used to set their values.

    • in an entry of a parameter specification dictionary assigned to the params argument of the constructor for the Component. The entry must use the keyword FUNCTION_PARAMS as its key, and its value must be a dictionary containing the parameters and their values. The key for each entry in the FUNCTION_PARAMS dictionary must be the name of a parameter, and its value the parameter’s value, as in the example below:

      my_component = SomeComponent(function=SomeFunction
                                   params={FUNCTION_PARAMS:{SOME_PARAM=1, SOME_OTHER_PARAM=2}})
      

    The parameters of functions for some Components may allow other forms of specification (see Specifying Parameters for details concerning different ways in which the value of a parameter can be specified).

Informational Attributes

In addition to its user-modifiable parameters, a Component has attributes that provide information about its contents and/or state, but do not directly affect its operation. Every Component has the following two informational attributes:

  • current_execution_count – maintains a record of the number of times a Component has executed; it excludes the executions carried out during initialization and validation, but includes all other executions, whether they are of the Component on its own are as part of a Compositions (e.g., Process or System). The value can be changed “manually” or programmatically by assigning an integer value directly to the attribute.
  • current_execution_time – maintains the Time of the last execution of the Component in the context of a System’s scheduler, and is stored as a time tuple of values indicating the TimeScale.TRIAL, TimeScale.PASS, and TimeScale.TIME_STEP of the last execution. Note that a System has two schedulers – scheduler_processing and scheduler_learning; current_execution_time stores the time of whichever of these was the last to execute the Component.

Component Methods

  • assign_params - assign the value of one or more parameters of a Component. Each parameter is specified as an entry in a parameter specification dictionary in the request_set argument; parameters for the Component’s function are specified as entries in a FUNCTION_PARAMS dict within request_set dict.
  • reset_params - reset the value of all user_params to a set of default values as specified in its mode argument, using a value of ResetMode.

Execution

Calls the execute method of the subclass that, in turn, calls its function.

Class Reference

class psyneulink.components.component.ResetMode

ResetModes used for reset_params:

CURRENT_TO_INSTANCE_DEFAULTS
  • resets all paramsCurrent values to paramInstanceDefaults values.
INSTANCE_TO_CLASS
  • resets all paramInstanceDefaults values to paramClassDefaults values.
ALL_TO_CLASS_DEFAULTS
  • resets all paramsCurrent and paramInstanceDefaults values to paramClassDefafults values
class psyneulink.components.component.DefaultsFlexibility

Denotes how rigid an assignment to a default is. That is, how much, if at all it can be modified to suit the purpose of a method/owner/etc.

e.g. when assigning a Function to a Mechanism:

pnl.TransferMechanism(default_variable=[0, 0], function=pnl.Linear())

the Linear function is assigned a default variable ([0]) based on it’s ClassDefault, which conflicts with the default variable specified by its future owner ([0, 0]). Since the default for Linear was not explicitly stated, we allow the TransferMechanism to reassign the Linear’s default variable as needed (FLEXIBLE)

FLEXIBLE

can be modified in any way

RIGID

cannot be modifed in any way

INCREASE_DIMENSION

can be wrapped in a single extra dimension

class psyneulink.components.component.Component(default_variable, param_defaults, size=NotImplemented, function=None, name=None, prefs=None)

Base class for Component.

Note

Component is an abstract class and should NEVER be instantiated by a direct call to its constructor. It should be instantiated using the constructor for a subclass.

variable

2d np.array – see variable

size

int or array of ints – see size

function

Function, function or method – see function

function_params

Dict[param_name: param_value] – see function_params

function_object

Function – see function_object

user_params

Dict[param_name: param_value] – see user_params

value

2d np.array – see value

log

Log – see log

current_execution_count

int – see current_execution_count

current_execution_time

tuple(Time.RUN, Time.TRIAL, Time.PASS, Time.TIME_STEP) – see current_execution_time

reinitialize_when

Condition

name : str
see name
prefs : PreferenceSet
see prefs
assign_params(request_set=None, context=None)

Validates specified params, adds them TO paramInstanceDefaults, and instantiates any if necessary

Call _instantiate_defaults with context = COMMAND_LINE, and “validated_set” as target_set. Update paramInstanceDefaults with validated_set so that any instantiations (below) are done in proper context. Instantiate any items in request set that require it (i.e., function or states).

reset_params(mode=<ResetMode.INSTANCE_TO_CLASS: 1>)

Reset current and/or instance defaults

If called with:
  • CURRENT_TO_INSTANCE_DEFAULTS all current param settings are set to instance defaults
  • INSTANCE_TO_CLASS all instance defaults are set to class defaults
  • ALL_TO_CLASS_DEFAULTS all current and instance param settings are set to class defaults
Parameters:mode – (ResetMode) - determines which params are reset
Return none:
reinitialize(*args)

If the component’s execute method involves execution of an Integrator Function, this method effectively begins the function’s accumulation over again at the specified value, and may update related values on the component, depending on the component type.

current_execution_count

Maintains a simple count of executions over the life of the Component, Incremented in the Component’s execute method by call to self._increment_execution_count

loggable_items

Diciontary of items that can be logged in the Component’s log and their current ContextFlags. This is a convenience method that calls the loggable_items property of the Component’s log.

set_log_conditions(items log_condition=EXECUTION)

Specifies items to be logged; these must be be loggable_items of the Component’s log. This is a convenience method that calls the set_log_conditions method of the Component’s log.

log_values(entries)

Specifies items to be logged; ; these must be be loggable_items of the Component’s log. This is a convenience method that calls the log_values method of the Component’s log.

logged_items

Dictionary of all items that have entries in the log, and their currently assigned ContextFlagss This is a convenience method that calls the logged_items property of the Component’s log.