def __init__(
            self,
            system: tc.optional(System_Base) = None,
            monitored_output_states=None,
            function=None,
            # control_signals:tc.optional(list) = None,
            control_signals=None,
            modulation: tc.optional(
                _is_modulation_param) = ModulationParam.MULTIPLICATIVE,
            params=None,
            name=None,
            prefs: is_pref_set = None):

        # Assign args to params and functionParams dicts
        params = self._assign_args_to_param_dicts(
            function=function, control_signals=control_signals, params=params)

        super().__init__(
            system=system,
            objective_mechanism=ObjectiveMechanism(
                monitored_output_states=monitored_output_states,
                function=DualAdaptiveIntegrator),
            control_signals=control_signals,
            modulation=modulation,
            params=params,
            name=name,
            prefs=prefs,
        )

        self.objective_mechanism.name = self.name + '_ObjectiveMechanism'
        self.objective_mechanism._role = CONTROL
示例#2
0
    def test_converging_pathways(self):
        a = TransferMechanism(name="a",
                              default_variable=[0, 0, 0])
        b = TransferMechanism(name="b")
        c = TransferMechanism(name="c",
                              default_variable=[0, 0, 0, 0, 0])
        LC = LCControlMechanism(modulated_mechanisms=[a,b],
                                objective_mechanism=ObjectiveMechanism(function=Linear,
                                                                       monitor=[b],
                                                                       name='lc_om'),
                                name="lc"
                                )
        p = Process(name="p",
                    pathway=[a, c])
        p2 = Process(name="p2",
                    pathway=[b, c])
        s = System(name="s",
                   processes=[p, p2])

        a_label = s._get_label(a, ALL)
        b_label = s._get_label(b, ALL)
        c_label = s._get_label(c, ALL)

        assert "out (3)" in a_label and "in (3)" in a_label
        assert "out (1)" in b_label and "in (1)" in b_label
        assert "out (5)" in c_label and "in (5)" in c_label
示例#3
0
    def __init__(
            self,
            system: tc.optional(System_Base) = None,
            monitored_output_ports=None,
            function=None,
            # control_signals:tc.optional(list) = None,
            control_signals=None,
            modulation: tc.optional(str) = MULTIPLICATIVE,
            params=None,
            name=None,
            prefs: is_pref_set = None):

        super().__init__(
            system=system,
            objective_mechanism=ObjectiveMechanism(
                monitored_output_ports=monitored_output_ports,
                function=DualAdaptiveIntegrator),
            control_signals=control_signals,
            modulation=modulation,
            params=params,
            name=name,
            prefs=prefs,
        )

        self.objective_mechanism.name = self.name + '_ObjectiveMechanism'
        self.objective_mechanism._role = CONTROL
示例#4
0
    def test_objective_mech_inputs_list_of_ints(self, benchmark, mech_mode):

        O = ObjectiveMechanism(
            name='O',
            default_variable=[0 for i in range(VECTOR_SIZE)],
        )
        EX = pytest.helpers.get_mech_execution(O, mech_mode)

        val = benchmark(EX, [10.0 for i in range(VECTOR_SIZE)])
        assert np.allclose(val, [[10.0 for i in range(VECTOR_SIZE)]])
 def test_alias_equivalence_for_modulates_and_projections(self):
     inputs = [1, 9, 4, 3, 2]
     comp1 = Composition()
     tMech1 = TransferMechanism()
     tMech2 = TransferMechanism()
     cMech1 = ControlMechanism(
         control_signals=ControlSignal(modulates=(SLOPE, tMech2)),
         objective_mechanism=ObjectiveMechanism(monitor=(RESULT, tMech2)))
     comp1.add_nodes([tMech1, tMech2, cMech1])
     comp1.add_linear_processing_pathway([cMech1, tMech1, tMech2])
     comp1.run(inputs=inputs)
     comp2 = Composition()
     tMech3 = TransferMechanism()
     tMech4 = TransferMechanism()
     cMech2 = ControlMechanism(
         control_signals=ControlSignal(projections=(SLOPE, tMech4)),
         objective_mechanism=ObjectiveMechanism(monitor=(RESULT, tMech4)))
     comp2.add_nodes([tMech3, tMech4, cMech2])
     comp2.add_linear_processing_pathway([cMech2, tMech3, tMech4])
     comp2.run(inputs=inputs)
     assert comp1.results == comp2.results
示例#6
0
    def test_objective_mech_inputs_list_of_ints(self, benchmark, mode):

        O = ObjectiveMechanism(
            name='O',
            default_variable=[0 for i in range(VECTOR_SIZE)],
        )
        if mode == 'Python':
            EX = O.execute
        elif mode == 'LLVM':
            e = pnlvm.execution.MechExecution(O)
            EX = e.execute
        elif mode == 'PTX':
            e = pnlvm.execution.MechExecution(O)
            EX = e.cuda_execute

        val = benchmark(EX, [10.0 for i in range(VECTOR_SIZE)])

        assert np.allclose(val, [[10.0 for i in range(VECTOR_SIZE)]])
示例#7
0
    def __init__(self,
                 monitored_output_ports=None,
                 function=None,
                 # control_signals:tc.optional(tc.optional(list)) = None,
                 control_signals= None,
                 modulation:tc.optional(str)=None,
                 params=None,
                 name=None,
                 prefs:is_pref_set=None):

        super().__init__(
            objective_mechanism=ObjectiveMechanism(
                monitored_output_ports=monitored_output_ports,
                function=DualAdaptiveIntegrator
            ),
            control_signals=control_signals,
            modulation=modulation,
            params=params,
            name=name,
            prefs=prefs,
        )

        self.objective_mechanism.name = self.name + '_ObjectiveMechanism'
示例#8
0
def test_predator_prey(benchmark, mode, samples):
    if len(samples) > 10 and mode not in {"LLVM", "LLVMRun", "Python-PTX"}:
        pytest.skip("This test takes too long")
    # OCM default mode is Python
    mode, ocm_mode = (mode + "-Python").split('-')[0:2]
    benchmark.group = "Predator-Prey " + str(len(samples))
    obs_len = 3
    obs_coords = 2
    player_idx = 0
    player_obs_start_idx = player_idx * obs_len
    player_value_idx = player_idx * obs_len + obs_coords
    player_coord_slice = slice(player_obs_start_idx,player_value_idx)
    predator_idx = 1
    predator_obs_start_idx = predator_idx * obs_len
    predator_value_idx = predator_idx * obs_len + obs_coords
    predator_coord_slice = slice(predator_obs_start_idx,predator_value_idx)
    prey_idx = 2
    prey_obs_start_idx = prey_idx * obs_len
    prey_value_idx = prey_idx * obs_len + obs_coords
    prey_coord_slice = slice(prey_obs_start_idx,prey_value_idx)

    player_len = prey_len = predator_len = obs_coords

    # Perceptual Mechanisms
    player_obs = ProcessingMechanism(size=prey_len, function=GaussianDistort, name="PLAYER OBS")
    prey_obs = ProcessingMechanism(size=prey_len, function=GaussianDistort, name="PREY OBS")
    predator_obs = TransferMechanism(size=predator_len, function=GaussianDistort, name="PREDATOR OBS")

    # Action Mechanism
    #    Use ComparatorMechanism to compute direction of action as difference of coordinates between player and prey:
    #    note: unitization is done in main loop, to allow compilation of LinearCombination function) (TBI)
    greedy_action_mech = ComparatorMechanism(name='ACTION',sample=player_obs,target=prey_obs)

    # Create Composition
    agent_comp = Composition(name='PREDATOR-PREY COMPOSITION')
    agent_comp.add_node(player_obs)
    agent_comp.add_node(predator_obs)
    agent_comp.add_node(prey_obs)
    agent_comp.add_node(greedy_action_mech)
    agent_comp.exclude_node_roles(predator_obs, NodeRole.OUTPUT)

    ocm = OptimizationControlMechanism(features={SHADOW_INPUTS: [player_obs, predator_obs, prey_obs]},
                                       agent_rep=agent_comp,
                                       function=GridSearch(direction=MINIMIZE,
                                                           save_values=True),

                                       objective_mechanism=ObjectiveMechanism(function=Distance(metric=NORMED_L0_SIMILARITY),
                                                                              monitor=[
                                                                                  player_obs,
                                                                                  prey_obs
                                                                              ]),
                                       control_signals=[ControlSignal(modulates=(VARIANCE,player_obs),
                                                                      allocation_samples=samples),
                                                        ControlSignal(modulates=(VARIANCE,predator_obs),
                                                                      allocation_samples=samples),
                                                        ControlSignal(modulates=(VARIANCE,prey_obs),
                                                                      allocation_samples=samples)
                                                        ],
                                       )
    agent_comp.add_controller(ocm)
    agent_comp.enable_controller = True
    ocm.comp_execution_mode = ocm_mode

    input_dict = {player_obs:[[1.1576537,  0.60782117]],
                  predator_obs:[[-0.03479106, -0.47666293]],
                  prey_obs:[[-0.60836214,  0.1760381 ]],
                 }
    run_results = agent_comp.run(inputs=input_dict, num_trials=2, bin_execute=mode)

    if len(samples) == 2:
        # KDM 12/4/19: modified results due to global seed offset of
        # GaussianDistort assignment.
        # to produce old numbers, run get_global_seed once before creating
        # each Mechanism with GaussianDistort above
        assert np.allclose(run_results[0], [[-10.06333025,   2.4845505 ]])
        if mode == 'Python':
            assert np.allclose(ocm.feature_values, [[ 1.1576537,   0.60782117],
                                                    [-0.03479106, -0.47666293],
                                                    [-0.60836214,  0.1760381 ]])

    if benchmark.enabled:
        benchmark(agent_comp.run, inputs=input_dict, bin_execute=mode)
def test_predator_prey(benchmark, mode, samples):
    benchmark.group = "Predator-Prey " + str(len(samples))
    # These should probably be replaced by reference to ForagerEnv constants:
    obs_len = 3
    obs_coords = 2
    action_len = 2
    player_idx = 0
    player_obs_start_idx = player_idx * obs_len
    player_value_idx = player_idx * obs_len + obs_coords
    player_coord_slice = slice(player_obs_start_idx, player_value_idx)
    predator_idx = 1
    predator_obs_start_idx = predator_idx * obs_len
    predator_value_idx = predator_idx * obs_len + obs_coords
    predator_coord_slice = slice(predator_obs_start_idx, predator_value_idx)
    prey_idx = 2
    prey_obs_start_idx = prey_idx * obs_len
    prey_value_idx = prey_idx * obs_len + obs_coords
    prey_coord_slice = slice(prey_obs_start_idx, prey_value_idx)

    player_len = prey_len = predator_len = obs_coords

    # Perceptual Mechanisms
    player_obs = ProcessingMechanism(size=prey_len,
                                     function=GaussianDistort,
                                     name="PLAYER OBS")
    prey_obs = ProcessingMechanism(size=prey_len,
                                   function=GaussianDistort,
                                   name="PREY OBS")
    predator_obs = TransferMechanism(size=predator_len,
                                     function=GaussianDistort,
                                     name="PREDATOR OBS")

    # Action Mechanism
    #    Use ComparatorMechanism to compute direction of action as difference of coordinates between player and prey:
    #    note: unitization is done in main loop, to allow compilation of LinearCombination function) (TBI)
    greedy_action_mech = ComparatorMechanism(name='ACTION',
                                             sample=player_obs,
                                             target=prey_obs)

    # Create Composition
    agent_comp = Composition(name='PREDATOR-PREY COMPOSITION')
    agent_comp.add_node(player_obs)
    agent_comp.add_node(predator_obs)
    agent_comp.add_node(prey_obs)
    agent_comp.add_node(greedy_action_mech)

    # ControlMechanism

    ocm = OptimizationControlMechanism(
        features={SHADOW_INPUTS: [player_obs, predator_obs, prey_obs]},
        agent_rep=agent_comp,
        function=GridSearch(direction=MINIMIZE, save_values=True),
        objective_mechanism=ObjectiveMechanism(
            function=Distance(metric=NORMED_L0_SIMILARITY),
            monitor=[player_obs, predator_obs, prey_obs]),
        control_signals=[
            ControlSignal(modulates=(VARIANCE, player_obs),
                          allocation_samples=samples),
            ControlSignal(modulates=(VARIANCE, predator_obs),
                          allocation_samples=samples),
            ControlSignal(modulates=(VARIANCE, prey_obs),
                          allocation_samples=samples),
        ],
    )
    agent_comp.add_controller(ocm)
    agent_comp.enable_controller = True
    ocm.comp_execution_mode = mode

    input_dict = {
        player_obs: [[1.1576537, 0.60782117]],
        predator_obs: [[-0.03479106, -0.47666293]],
        prey_obs: [[-0.60836214, 0.1760381]],
    }
    run_results = agent_comp.run(inputs=input_dict,
                                 num_trials=2,
                                 bin_execute=mode)

    if len(samples) == 2:
        assert np.allclose(run_results[0], [[-19.06547277, 5.47274121]])
        if mode == 'Python':
            assert np.allclose(
                ocm.feature_values,
                [[1.1576537, 0.60782117], [-0.03479106, -0.47666293],
                 [-0.60836214, 0.1760381]])

    benchmark(agent_comp.run, inputs=input_dict, bin_execute=mode)
示例#10
0
def test_moving_average(mode):

    # Set an arbitrary seed and a global random state to keep the randomly generated quantities the same between runs
    seed = 20170530  # this will be separately given to ELFI
    np.random.seed(seed)

    # true parameters
    t1_true = 0.6
    t2_true = 0.2

    # Define a function that simulates a 2nd order moving average, assuming mean zero:
    # y_t = w_t + t1*w_t-1 + t2*w_t-2
    # where t1 and t2 are real and w_k is i.i.d sequence white noise with N(0,1)
    def MA2(input=[0],
            t1=0.5,
            t2=0.5,
            n_obs=100,
            batch_size=1,
            random_state=None):
        # FIXME: Convert arguments to scalar if they are not. Why is this nescessary?
        # PsyNeuLink, when creating a user defined function, seems to expect the function
        # to support inputs of type np.ndarray even when they are only allowed to be
        # scalars.
        n_obs = n_obs[0] if (type(n_obs) is np.ndarray) else n_obs
        batch_size = batch_size[0] if (
            type(batch_size) is np.ndarray) else batch_size

        # Make inputs 2d arrays for numpy broadcasting with w
        t1 = np.asanyarray(t1).reshape((-1, 1))
        t2 = np.asanyarray(t2).reshape((-1, 1))
        random_state = random_state or np.random

        w = random_state.randn(int(batch_size),
                               int(n_obs) + 2)  # i.i.d. sequence ~ N(0,1)
        x = w[:, 2:] + t1 * w[:, 1:-1] + t2 * w[:, :-2]
        return x

    # Lets make some observed data. This will be the data we try to fit parameters for.
    y_obs = MA2(t1=t1_true, t2=t2_true)

    # Make a processing mechanism out of our simulator.
    ma_mech = ProcessingMechanism(function=MA2,
                                  size=1,
                                  name='Moving Average (2nd Order)')

    # Now lets add it to a composition
    comp = Composition(name="Moving_Average")
    comp.add_node(ma_mech)

    # Now lets setup some control signals for the parameters we want to
    # infer. This is where we would like to specify priors.
    signalSearchRange = SampleSpec(start=0.1, stop=2.0, step=0.2)
    t1_control_signal = ControlSignal(projections=[('t1', ma_mech)],
                                      allocation_samples=signalSearchRange,
                                      cost_options=[],
                                      modulation=OVERRIDE)
    t2_control_signal = ControlSignal(projections=[('t2', ma_mech)],
                                      allocation_samples=signalSearchRange,
                                      cost_options=[],
                                      modulation=OVERRIDE)

    # A function to calculate the auto-covariance with specific lag for a
    # time series. We will use this function to compute the summary statistics
    # for generated and observed data so that we can compute a metric between the
    # two. In PsyNeuLink terms, this will be part of an ObjectiveMechanism.
    def autocov(agent_rep, x=None, lag=1):
        if x is None:
            return np.asarray(0.0)

        C = np.mean(x[:, lag:] * x[:, :-lag], axis=1)
        return C

    # # Lets make one function that computes all the summary stats in one go because PsyNeuLink
    # # objective mechanism expect a single function.
    # def objective_function(x):
    #     return np.concatenate((autocov(x), autocov(x, lag=2)))
    #
    # # Objective Mechanism and its function currently need to be specified in the script.
    # # (In future versions, this will be set up automatically)
    # objective_mech = ObjectiveMechanism(function=objective_function,
    #                                         monitor=[ma_mech])

    # Setup the controller with the ParamEstimationFunction
    if mode == 'elfi':
        comp.add_controller(controller=OptimizationControlMechanism(
            agent_rep=comp,
            function=ParamEstimationFunction(
                priors={
                    't1': (scipy.stats.uniform, 0, 2),
                    't2': (scipy.stats.uniform, 0, 2)
                },
                observed=y_obs,
                summary=[(autocov, 1), (autocov, 2)],
                discrepancy='euclidean',
                n_samples=3,
                quantile=0.01,  # Set very small now cause things are slow.
                seed=seed),
            objective_mechanism=False,
            control_signals=[t1_control_signal, t2_control_signal]))
    elif mode == 'GridSearch':
        observed_C = np.array(
            [autocov(None, y_obs, 1),
             autocov(None, y_obs, 2)])

        def objective_f(val):
            C = np.array([autocov(None, val, 1), autocov(None, val, 2)])
            ret = np.linalg.norm(C - observed_C)
            return ret

        objective_mech = ObjectiveMechanism(function=objective_f,
                                            size=len(y_obs[0]),
                                            monitor=[ma_mech],
                                            name='autocov - observed autocov')
        comp.add_controller(controller=OptimizationControlMechanism(
            agent_rep=comp,
            function=GridSearch(save_values=True, direction=MINIMIZE),
            objective_mechanism=objective_mech,
            control_signals=[t1_control_signal, t2_control_signal]))

    comp.disable_all_history()

    # Lets setup some input to the mechanism, not that it uses it for anything.
    stim_list_dict = {ma_mech: [0]}

    # # FIXME: Show graph fails when the controller doesn't have an objective mechanism.
    # comp.show_graph(show_controller=True,
    #                 show_projection_labels=True,
    #                 show_node_structure=True,
    #                 show_cim=True,
    #                 show_dimensions=True)

    comp.run(inputs=stim_list_dict)

    if mode == 'elfi':
        assert np.allclose(comp.controller.value, [[0.5314349], [0.19140103]])
    if mode == 'GridSearch':
        assert np.allclose(comp.controller.value, [[0.5], [0.3]])