def code_object(self, owner, name, abstract_code, variables, template_name, variable_indices, codeobj_class=None, template_kwds=None, override_conditional_write=None, compiler_kwds=None): if compiler_kwds is None: compiler_kwds = {} name = find_name(name) codeobj_class = self.code_object_class(codeobj_class) template = getattr(codeobj_class.templater, template_name) iterate_all = template.iterate_all generator = codeobj_class.generator_class(variables=variables, variable_indices=variable_indices, owner=owner, iterate_all=iterate_all, codeobj_class=codeobj_class, override_conditional_write=override_conditional_write, allows_scalar_write=template.allows_scalar_write, name=name, template_name=template_name) if template_kwds is None: template_kwds = dict() else: template_kwds = template_kwds.copy() logger.diagnostic('%s abstract code:\n%s' % (name, indent(code_representation(abstract_code)))) scalar_code, vector_code, kwds = generator.translate(abstract_code, dtype=prefs['core.default_float_dtype']) # Add the array names as keywords as well for varname, var in variables.items(): if isinstance(var, ArrayVariable): pointer_name = generator.get_array_name(var) if var.scalar: pointer_name += '[0]' template_kwds[varname] = pointer_name if hasattr(var, 'resize'): dyn_array_name = generator.get_array_name(var, access_data=False) template_kwds['_dynamic_'+varname] = dyn_array_name template_kwds.update(kwds) logger.diagnostic('%s snippet (scalar):\n%s' % (name, indent(code_representation(scalar_code)))) logger.diagnostic('%s snippet (vector):\n%s' % (name, indent(code_representation(vector_code)))) code = template(scalar_code, vector_code, owner=owner, variables=variables, codeobj_name=name, variable_indices=variable_indices, get_array_name=generator.get_array_name, **template_kwds) logger.diagnostic('%s code:\n%s' % (name, indent(code_representation(code)))) codeobj = codeobj_class(owner, code, variables, variable_indices, template_name=template_name, template_source=template.template_source, name=name, compiler_kwds=compiler_kwds) codeobj.compile() return codeobj
def code_object(self, owner, name, abstract_code, variables, template_name, variable_indices, codeobj_class=None, template_kwds=None, override_conditional_write=None, compiler_kwds=None): if compiler_kwds is None: compiler_kwds = {} name = find_name(name) codeobj_class = self.code_object_class(codeobj_class) template = getattr(codeobj_class.templater, template_name) iterate_all = template.iterate_all generator = codeobj_class.generator_class(variables=variables, variable_indices=variable_indices, owner=owner, iterate_all=iterate_all, codeobj_class=codeobj_class, override_conditional_write=override_conditional_write, allows_scalar_write=template.allows_scalar_write, name=name, template_name=template_name) if template_kwds is None: template_kwds = dict() else: template_kwds = template_kwds.copy() logger.diagnostic('%s abstract code:\n%s' % (name, indent(code_representation(abstract_code)))) scalar_code, vector_code, kwds = generator.translate(abstract_code, dtype=prefs['core.default_float_dtype']) # Add the array names as keywords as well for varname, var in variables.iteritems(): if isinstance(var, ArrayVariable): pointer_name = generator.get_array_name(var) if var.scalar: pointer_name += '[0]' template_kwds[varname] = pointer_name if hasattr(var, 'resize'): dyn_array_name = generator.get_array_name(var, access_data=False) template_kwds['_dynamic_'+varname] = dyn_array_name template_kwds.update(kwds) logger.diagnostic('%s snippet (scalar):\n%s' % (name, indent(code_representation(scalar_code)))) logger.diagnostic('%s snippet (vector):\n%s' % (name, indent(code_representation(vector_code)))) code = template(scalar_code, vector_code, owner=owner, variables=variables, codeobj_name=name, variable_indices=variable_indices, get_array_name=generator.get_array_name, **template_kwds) logger.diagnostic('%s code:\n%s' % (name, indent(code_representation(code)))) codeobj = codeobj_class(owner, code, variables, variable_indices, template_name=template_name, template_source=template.template_source, name=name, compiler_kwds=compiler_kwds) codeobj.compile() return codeobj
def code_object(self, owner, name, abstract_code, variables, template_name, variable_indices, codeobj_class=None, template_kwds=None, override_conditional_write=None): codeobj_class = self.code_object_class(codeobj_class) template = getattr(codeobj_class.templater, template_name) iterate_all = template.iterate_all generator = codeobj_class.generator_class(variables=variables, variable_indices=variable_indices, owner=owner, iterate_all=iterate_all, codeobj_class=codeobj_class, override_conditional_write=override_conditional_write, allows_scalar_write=template.allows_scalar_write, name=name, template_name=template_name) if template_kwds is None: template_kwds = dict() else: template_kwds = template_kwds.copy() # Check that all functions are available for varname, value in variables.iteritems(): if isinstance(value, Function): try: value.implementations[codeobj_class] except KeyError as ex: # if we are dealing with numpy, add the default implementation if codeobj_class is NumpyCodeObject: value.implementations.add_numpy_implementation(value.pyfunc) else: raise NotImplementedError(('Cannot use function ' '%s: %s') % (varname, ex)) logger.diagnostic('%s abstract code:\n%s' % (name, indent(code_representation(abstract_code)))) scalar_code, vector_code, kwds = generator.translate(abstract_code, dtype=prefs['core.default_float_dtype']) # Add the array names as keywords as well for varname, var in variables.iteritems(): if isinstance(var, ArrayVariable): pointer_name = generator.get_array_name(var) if var.scalar: pointer_name += '[0]' template_kwds[varname] = pointer_name if hasattr(var, 'resize'): dyn_array_name = generator.get_array_name(var, access_data=False) template_kwds['_dynamic_'+varname] = dyn_array_name template_kwds.update(kwds) logger.diagnostic('%s snippet (scalar):\n%s' % (name, indent(code_representation(scalar_code)))) logger.diagnostic('%s snippet (vector):\n%s' % (name, indent(code_representation(vector_code)))) name = find_name(name) code = template(scalar_code, vector_code, owner=owner, variables=variables, codeobj_name=name, variable_indices=variable_indices, get_array_name=generator.get_array_name, **template_kwds) logger.diagnostic('%s code:\n%s' % (name, indent(code_representation(code)))) codeobj = codeobj_class(owner, code, variables, variable_indices, template_name=template_name, template_source=template.template_source, name=name) codeobj.compile() return codeobj
def run_regularly(self, code, dt=None, clock=None, when='start', order=0, name=None, codeobj_class=None): """ Run abstract code in the group's namespace. The created `CodeRunner` object will be automatically added to the group, it therefore does not need to be added to the network manually. However, a reference to the object will be returned, which can be used to later remove it from the group or to set it to inactive. Parameters ---------- code : str The abstract code to run. dt : `Quantity`, optional The time step to use for this custom operation. Cannot be combined with the `clock` argument. clock : `Clock`, optional The update clock to use for this operation. If neither a clock nor the `dt` argument is specified, defaults to the clock of the group. when : str, optional When to run within a time step, defaults to the ``'start'`` slot. See :ref:`scheduling` for possible values. name : str, optional A unique name, if non is given the name of the group appended with 'run_regularly', 'run_regularly_1', etc. will be used. If a name is given explicitly, it will be used as given (i.e. the group name will not be prepended automatically). codeobj_class : class, optional The `CodeObject` class to run code with. If not specified, defaults to the `group`'s ``codeobj_class`` attribute. Returns ------- obj : `CodeRunner` A reference to the object that will be run. """ if name is None: names = [o.name for o in self.contained_objects] name = find_name(f"{self.name}_run_regularly*", names) if dt is None and clock is None: clock = self._clock # Subgroups are normally not included in their parent's # contained_objects list, since there's no need to include them in the # network (they don't perform any computation on their own). However, # if a subgroup declares a `run_regularly` operation, then we want to # include this operation automatically, i.e. with the parent group # (adding just the run_regularly operation to the parent group's # contained objects would no be enough, since the CodeObject needs a # reference to the group providing the context for the operation, i.e. # the subgroup instead of the parent group. See github issue #922 source_group = getattr(self, 'source', None) if source_group is not None: if not self in source_group.contained_objects: source_group.contained_objects.append(self) runner = CodeRunner(self, 'stateupdate', code=code, name=name, dt=dt, clock=clock, when=when, order=order, codeobj_class=codeobj_class) self.contained_objects.append(runner) return runner
def code_object(self, owner, name, abstract_code, variables, template_name, variable_indices, codeobj_class=None, template_kwds=None): codeobj_class = self.code_object_class(codeobj_class) language = codeobj_class.language if template_kwds is None: template_kwds = dict() else: template_kwds = template_kwds.copy() template = getattr(codeobj_class.templater, template_name) # Check that all functions are available for varname, value in variables.iteritems(): if isinstance(value, Function): try: value.implementations[codeobj_class] except KeyError as ex: # if we are dealing with numpy, add the default implementation if codeobj_class is NumpyCodeObject: add_numpy_implementation(value, value.pyfunc) else: raise NotImplementedError(('Cannot use function ' '%s: %s') % (varname, ex)) if isinstance(abstract_code, dict): for k, v in abstract_code.items(): logger.debug('%s abstract code key %s:\n%s' % (name, k, v)) else: logger.debug(name + " abstract code:\n" + abstract_code) iterate_all = template.iterate_all snippet, kwds = translate(abstract_code, variables, dtype=brian_prefs['core.default_scalar_dtype'], codeobj_class=codeobj_class, variable_indices=variable_indices, iterate_all=iterate_all) # Add the array names as keywords as well for varname, var in variables.iteritems(): if isinstance(var, ArrayVariable): pointer_name = language.get_array_name(var) template_kwds[varname] = pointer_name if hasattr(var, 'resize'): dyn_array_name = language.get_array_name(var, access_data=False) template_kwds['_dynamic_'+varname] = dyn_array_name template_kwds.update(kwds) logger.debug(name + " snippet:\n" + str(snippet)) name = find_name(name) code = template(snippet, owner=owner, variables=variables, codeobj_name=name, variable_indices=variable_indices, get_array_name=language.get_array_name, **template_kwds) logger.debug(name + " code:\n" + str(code)) codeobj = codeobj_class(owner, code, variables, name=name) codeobj.compile() return codeobj