def _apply_to_impl(self, instance, **kwds): self._config = self.CONFIG(kwds.pop('options', {})) self._config.set_value(kwds) targets = self._config.targets if targets is None: targets = (instance, ) knownBlocks = {} for t in targets: # check that t is in fact a child of instance if not is_child_of( parent=instance, child=t, knownBlocks=knownBlocks): raise GDP_Error( "Target '%s' is not a component on instance '%s'!" % (t.name, instance.name)) elif t.ctype is Disjunction: if t.is_indexed(): self._transform_disjunction(t) else: self._transform_disjunctionData(t, t.index()) elif t.ctype in (Block, Disjunct): if t.is_indexed(): self._transform_block(t) else: self._transform_blockData(t) else: raise GDP_Error( "Target '%s' was not a Block, Disjunct, or Disjunction. " "It was of type %s and can't be transformed." % (t.name, type(t)))
def test_is_child_of(self): m = ConcreteModel() m.b = Block() m.b.b_indexed = Block([1,2]) m.b_parallel = Block() knownBlocks = {} self.assertFalse(is_child_of(parent=m.b, child=m.b_parallel, knownBlocks=knownBlocks)) self.assertEqual(len(knownBlocks), 2) self.assertFalse(knownBlocks.get(m)) self.assertFalse(knownBlocks.get(m.b_parallel)) self.assertTrue(is_child_of(parent=m.b, child=m.b.b_indexed[1], knownBlocks=knownBlocks)) self.assertEqual(len(knownBlocks), 4) self.assertFalse(knownBlocks.get(m)) self.assertFalse(knownBlocks.get(m.b_parallel)) self.assertTrue(knownBlocks.get(m.b.b_indexed[1])) self.assertTrue(knownBlocks.get(m.b.b_indexed))
def _apply_to_impl(self, instance, **kwds): self._config = self.CONFIG(kwds.pop('options', {})) self._config.set_value(kwds) targets = self._config.targets if targets is None: targets = (instance, ) _HACK_transform_whole_instance = True else: _HACK_transform_whole_instance = False knownBlocks = {} for t in targets: # check that t is in fact a child of instance if not is_child_of( parent=instance, child=t, knownBlocks=knownBlocks): raise GDP_Error( "Target '%s' is not a component on instance '%s'!" % (t.name, instance.name)) elif t.ctype is Disjunction: if t.is_indexed(): self._transform_disjunction(t) else: self._transform_disjunctionData(t, t.index()) elif t.ctype in (Block, Disjunct): if t.is_indexed(): self._transform_block(t) else: self._transform_blockData(t) else: raise GDP_Error( "Target '%s' was not a Block, Disjunct, or Disjunction. " "It was of type %s and can't be transformed." % (t.name, type(t))) # HACK for backwards compatibility with the older GDP transformations # # Until the writers are updated to find variables on things other than # active blocks, we need to reclassify the Disjuncts as Blocks after # transformation so that the writer will pick up all the variables that # it needs (in this case, indicator_vars and also variables which are # declared in a single Disjunct and only used on that Disjunct (as they # will not be disaggregated)). if _HACK_transform_whole_instance: HACK_GDP_Disjunct_Reclassifier().apply_to(instance)
def _apply_to_impl(self, instance, **kwds): config = self.CONFIG(kwds.pop('options', {})) # We will let args override suffixes and estimate as a last # resort. More specific args/suffixes override ones anywhere in # the tree. Suffixes lower down in the tree override ones higher # up. if 'default_bigM' in kwds: deprecation_warning("the 'default_bigM=' argument has been " "replaced by 'bigM='", version='5.4') config.bigM = kwds.pop('default_bigM') config.set_value(kwds) bigM = config.bigM self.assume_fixed_vars_permanent = config.assume_fixed_vars_permanent targets = config.targets if targets is None: targets = (instance, ) # We need to check that all the targets are in fact on instance. As we # do this, we will use the set below to cache components we know to be # in the tree rooted at instance. knownBlocks = {} for t in targets: # check that t is in fact a child of instance if not is_child_of(parent=instance, child=t, knownBlocks=knownBlocks): raise GDP_Error( "Target '%s' is not a component on instance '%s'!" % (t.name, instance.name)) elif t.ctype is Disjunction: if t.is_indexed(): self._transform_disjunction(t, bigM) else: self._transform_disjunctionData( t, bigM, t.index()) elif t.ctype in (Block, Disjunct): if t.is_indexed(): self._transform_block(t, bigM) else: self._transform_blockData(t, bigM) else: raise GDP_Error( "Target '%s' was not a Block, Disjunct, or Disjunction. " "It was of type %s and can't be transformed." % (t.name, type(t))) # issue warnings about anything that was in the bigM args dict that we # didn't use if bigM is not None: unused_args = ComponentSet(bigM.keys()) - \ ComponentSet(self.used_args.keys()) if len(unused_args) > 0: warning_msg = ("Unused arguments in the bigM map! " "These arguments were not used by the " "transformation:\n") for component in unused_args: if hasattr(component, 'name'): warning_msg += "\t%s\n" % component.name else: warning_msg += "\t%s\n" % component logger.warning(warning_msg)
def _apply_to_impl(self, instance, **kwds): config = self.CONFIG(kwds.pop('options', {})) # We will let args override suffixes and estimate as a last # resort. More specific args/suffixes override ones anywhere in # the tree. Suffixes lower down in the tree override ones higher # up. if 'default_bigM' in kwds: logger.warn("DEPRECATED: the 'default_bigM=' argument has been " "replaced by 'bigM='") config.bigM = kwds.pop('default_bigM') config.set_value(kwds) bigM = config.bigM targets = config.targets if targets is None: targets = (instance, ) _HACK_transform_whole_instance = True else: _HACK_transform_whole_instance = False # We need to check that all the targets are in fact on instance. As we # do this, we will use the set below to cache components we know to be # in the tree rooted at instance. knownBlocks = {} for t in targets: # check that t is in fact a child of instance if not is_child_of(parent=instance, child=t, knownBlocks=knownBlocks): raise GDP_Error("Target %s is not a component on instance %s!" % (t.name, instance.name)) elif t.ctype is Disjunction: if t.parent_component() is t: self._transform_disjunction(t, bigM) else: self._transform_disjunctionData( t, bigM, t.index()) elif t.ctype in (Block, Disjunct): if t.parent_component() is t: self._transform_block(t, bigM) else: self._transform_blockData(t, bigM) else: raise GDP_Error( "Target %s was not a Block, Disjunct, or Disjunction. " "It was of type %s and can't be transformed." % (t.name, type(t))) # issue warnings about anything that was in the bigM args dict that we # didn't use if bigM is not None: unused_args = ComponentSet(bigM.keys()) - \ ComponentSet(self.used_args.keys()) if len(unused_args) > 0: warning_msg = ("Unused arguments in the bigM map! " "These arguments were not used by the " "transformation:\n") for component in unused_args: if hasattr(component, 'name'): warning_msg += "\t%s\n" % component.name else: warning_msg += "\t%s\n" % component logger.warn(warning_msg) # HACK for backwards compatibility with the older GDP transformations # # Until the writers are updated to find variables on things # other than active blocks, we need to reclassify the Disjuncts # as Blocks after transformation so that the writer will pick up # all the variables that it needs (in this case, indicator_vars). if _HACK_transform_whole_instance: HACK_GDP_Disjunct_Reclassifier().apply_to(instance)
def _apply_to_impl(self, instance, **kwds): self._config = self.CONFIG(kwds.pop('options', {})) self._config.set_value(kwds) # make a transformation block transBlockName = unique_component_name(instance, '_pyomo_gdp_chull_relaxation') transBlock = Block() instance.add_component(transBlockName, transBlock) transBlock.relaxedDisjuncts = Block(Any) transBlock.lbub = Set(initialize=['lb', 'ub', 'eq']) transBlock.disjContainers = ComponentSet() targets = self._config.targets if targets is None: targets = (instance, ) _HACK_transform_whole_instance = True else: _HACK_transform_whole_instance = False knownBlocks = {} for t in targets: # check that t is in fact a child of instance if not is_child_of( parent=instance, child=t, knownBlocks=knownBlocks): raise GDP_Error( "Target %s is not a component on instance %s!" % (t.name, instance.name)) elif t.type() is Disjunction: if t.parent_component() is t: self._transformDisjunction(t, transBlock) else: self._transformDisjunctionData(t, transBlock, t.index()) elif t.type() in (Block, Disjunct): if t.parent_component() is t: self._transformBlock(t, transBlock) else: self._transformBlockData(t, transBlock) else: raise GDP_Error( "Target %s was not a Block, Disjunct, or Disjunction. " "It was of type %s and can't be transformed" % (t.name, type(t))) # Go through our dictionary of indexed things and deactivate # the containers that don't have any active guys inside of # them. So the invalid component logic will tell us if we # missed something getting transformed. for obj in transBlock.disjContainers: if not obj.active: continue for i in obj: if obj[i].active: break else: # HACK due to active flag implementation. # # Ideally we would not have to do any of this (an # ActiveIndexedComponent would get its active status by # querring the active status of all the contained Data # objects). As a fallback, we would like to call: # # obj._deactivate_without_fixing_indicator() # # However, the sreaightforward implementation of that # method would have unintended side effects (fixing the # contained _DisjunctData's indicator_vars!) due to our # class hierarchy. Instead, we will directly call the # relevant base class (safe-ish since we are verifying # that all the contained _DisjunctionData are # deactivated directly above). ActiveComponent.deactivate(obj) # HACK for backwards compatibility with the older GDP transformations # # Until the writers are updated to find variables on things # other than active blocks, we need to reclassify the Disjuncts # as Blocks after transformation so that the writer will pick up # all the variables that it needs (in this case, indicator_vars). if _HACK_transform_whole_instance: HACK_GDP_Disjunct_Reclassifier().apply_to(instance)