Changeset 2865


Ignore:
Timestamp:
Jul 27, 2010 8:05:29 PM (9 years ago)
Author:
wehart
Message:

Adding a Block component, which is a base class for Model.

Note that this is a preliminary implementation. I haven't added added logic for recursing through subblocks.
To retain backwards compatibility, we don't need that functionality.

Location:
coopr.pyomo/trunk
Files:
2 added
12 edited

Legend:

Unmodified
Added
Removed
  • coopr.pyomo/trunk/coopr/pyomo/base/PyomoModel.py

    r2843 r2865  
    2929import pyomo
    3030
    31 from component import *
    32 from sets import Set, _ProductSet, _SetContainer, _BaseSet
    33 from rangeset import RangeSet
    34 from var import Var
    35 from constraint import Constraint, ConstraintData, ConstraintBase
    36 from objective import Objective
    37 from param import Param
    38 
    39 
    40 class Model(Component):
     31from block import Block
     32from sets import Set
     33
     34
     35class Model(Block):
    4136    """
    4237    An optimization model.  By default, this defers construction of components
     
    5146    def __init__(self, name="unknown"):
    5247        """Constructor"""
    53         Component.__init__(self, ctype=Model)
    54         self._defer_construction=True
    55         #
    56         # Define component dictionary: component type -> instance
    57         #
    58         self._component={}
    59         for item in ModelComponentFactory.services():
    60             self._component[  ModelComponentFactory.get_class(item) ] = {}
    61         #
    62         # A list of the declarations, in the order that they are
    63         # specified.
    64         #
    65         self._declarations=[]
     48        Block.__init__(self, ctype=Model)
     49        #
    6650        # the _name_varmap and _name_conmap dictionarys are assigned when
    6751        # the problem definition file is written, i.e., via the write()
    6852        # command. intent is to map names that will be coming back from
    6953        # a solver into Pyomo variables. Values are of type _VarValue.
     54        #
    7055        self._name_varmap={}
    7156        self._name_conmap={}
     
    8570        #
    8671        self.statistics = Container()
    87 
     72        #
    8873        # We make the default behavior of has_capabilities to lie and return
    8974        # True. We do this to allow the richest output formats when no
     
    9378        # We define _tempTrue since using self.has_capability = lambda x: True
    9479        # causes pickling errors.
     80        #
    9581        self.has_capability = _tempTrue
    96 
    97     def concrete_mode(self):
    98         self._defer_construction=False
    99 
    100     def symbolic_mode(self):
    101         self._defer_construction=True
    102 
    103     def components(self, ctype=None):
    104         if ctype is None:
    105             return self._component
    106         if ctype in self._component:
    107              return self._component[ctype]
    108         raise KeyError, "Unknown component type: %s" % str(ctype)
    10982
    11083    def nvariables(self):
     
    144117        return self._name_objmap
    145118
    146 
    147     def active_components(self, _ctype=None):
    148         tmp = {}
    149         if _ctype is None:
    150             for ctype in self._component:
    151                 tmp[ctype]={}
    152         elif _ctype in self._component:
    153             tmp[_ctype]={}
    154         else:
    155             raise KeyError, "Unknown component type: %s" % str(_ctype)
    156         for ctype in tmp:
    157             for name in self._component[ctype]:
    158                 comp = self._component[ctype][name]
    159                 if comp.active:
    160                     tmp[ctype][name] = comp
    161         if not _ctype is None:
    162             return tmp[_ctype]
    163         #print "ACTIVE",tmp
    164         return tmp
    165 
    166119    def num_used_variables(self):
    167120        return len(self._var)
    168121
    169 
    170122    def valid_problem_types(self):
    171123        return [ProblemFormat.pyomo]
    172 
    173 
    174     def _add_temporary_set(self,val):
    175         if val._index_set is not None:
    176             ctr=0
    177             for tset in val._index_set:
    178                 if tset.name == "_unknown_":
    179                     self._construct_temporary_set(
    180                       tset,
    181                       val.name+"_index_"+str(ctr)
    182                     )
    183                 ctr += 1
    184             val._index = self._construct_temporary_set(
    185               val._index_set,
    186               val.name+"_index"
    187             )
    188         if isinstance(val._index,_SetContainer) and \
    189             val._index.name == "_unknown_":
    190             self._construct_temporary_set(val._index,val.name+"_index")
    191         if val.domain is not None and val.domain.name == "_unknown_":
    192             self._construct_temporary_set(val.domain,val.name+"_domain")
    193 
    194 
    195     def _construct_temporary_set(self, obj, name):
    196         if type(obj) is tuple:
    197            if len(obj) == 1:                #pragma:nocover
    198                   raise Exception, "Unexpected temporary set construction"
    199            else:
    200                   tobj=_ProductSet(*obj)
    201                   setattr(self,name,tobj)
    202                   tobj.virtual=True
    203                   return tobj
    204         if isinstance(obj,_BaseSet):
    205            setattr(self,name,obj)
    206            return obj
    207 
    208 
    209     def _clear_attribute(self,name):
    210         #
    211         # cleanup the pre-existing model attribute
    212         #
    213         i=0
    214         for decl in self._declarations:
    215             if decl.name == name:
    216                 self.__dict__[name]=None
    217                 del self._declarations[i]
    218                 for item in self._component:
    219                     if name in self._component[item]:
    220                         del self._component[item][name]
    221                         break
    222                 break
    223             i += 1
    224 
    225     def _setattr_exec(self,name,val):
    226         if name in self.__dict__:
    227            self._clear_attribute(name)
    228         val.name=name
    229         self._add_temporary_set(val)
    230         self._component[val.type()][name]=val
    231         self._declarations.append(val)
    232         self.__dict__[name]=val
    233         if not val.type() is Model:
    234             val.model=self
    235         if not self._defer_construction:
    236             val.construct(None)
    237 
    238     def __setattr__(self,name,val):
    239         """Set attributes"""
    240         #
    241         # Set Model Declaration
    242         #
    243         if name != "_component":
    244             #
    245             # If this is a component type, then simply set it
    246             #
    247             if isinstance(val,Component):
    248                 self._setattr_exec(name,val)
    249                 return
    250 
    251         # Try to set the value. This may fail if the attribute does not already
    252         # exist in this model, if the set_value function is not defined, or if
    253         # a bad value is provided. In the latter case, a ValueError will be
    254         # thrown, which # we raise. Otherwise, this is an object that we need
    255         # to set directly.
    256         try:
    257             self.__dict__[name].set_value(val)
    258         except ValueError, e:
    259             raise
    260         except Exception, e:
    261             self.__dict__[name]=val
    262 
    263124
    264125    def create(self, filename=None, name=None, namespace=None, namespaces=None):
     
    282143        return instance
    283144
    284 
    285145    def clone(self):
    286146        """Create a copy of this model"""
    287147
    288         for declaration in self._declarations:
    289             declaration.model = None
     148        for name in self._declarations:
     149            self._declarations[name].model = None
    290150
    291151        instance = copy.deepcopy(self)
    292152
    293         for declaration in self._declarations:
    294             declaration.model = self
    295         for declaration in instance._declarations:
    296             declaration.model = instance
     153        for name in self._declarations:
     154            self._declarations[name].model = self
     155        for name in instance._declarations:
     156            instance._declarations[name].model = instance
    297157        return instance
    298158
    299 
    300159    def reset(self):
    301         for declaration in self._declarations:
    302             declaration.reset()
    303 
     160        for name in self._declarations:
     161            self._declarations[name].reset()
    304162
    305163    def preprocess(self):
     
    307165        for item in self._preprocessors:
    308166            self = Model.preprocessor_ep.service(item).preprocess(self)
    309 
    310167
    311168    def solution(self):
     
    315172            soln.append( self._var[i].value )
    316173        return soln
    317 
    318174
    319175    def load(self, arg, namespaces=[None]):
     
    353209            raise ValueError, msg % str( type(arg) )
    354210
    355 
    356211    def store_info(self, results):
    357212        """ Store model information into a SolverResults object """
     
    369224        for key in stat_keys:
    370225            results.problem.__dict__[key] = self.statistics.__dict__[key]
    371 
    372226
    373227    def _tuplize(self, data, setobj):
     
    383237        return ans
    384238
    385 
    386239    def _load_model_data(self, modeldata, namespaces):
    387240        """
     
    396249                raise IOError, msg % namespace
    397250        #print "HERE _load_model_data",self._declarations
    398         for declaration in self._declarations:
    399             if declaration.type() is Model:
     251        for tmp in self._declarations:
     252            if self._declarations[tmp].type() is Model:
    400253                continue
    401             tmp = declaration.name
     254            declaration = self._declarations[tmp]
    402255            if tmp in modeldata._default.keys():
    403256                if declaration.type() is Set:
     
    546399
    547400        return fname, symbol_map
    548 
    549 
    550     def pprint(self, filename=None, ostream=None):
    551         """
    552         Print a summary of the model info
    553         """
    554         if ostream is None:
    555            ostream = sys.stdout
    556         if filename is not None:
    557            OUTPUT=open(filename,"w")
    558            self.pprint(ostream=OUTPUT)
    559            OUTPUT.close()
    560            return
    561         if ostream is None:
    562            ostream = sys.stdout
    563         #
    564         # We hard-code the order of the core Pyomo modeling
    565         # components, to ensure that the output follows the logical
    566         # expected by a user.
    567         #
    568         items = [Set, RangeSet, Param, Var, Objective, Constraint]
    569         for item in pyutilib.component.core.ExtensionPoint(IModelComponent):
    570             if not item in items:
    571                 items.append(item)
    572         for item in items:
    573             if not item in self._component:
    574                 continue
    575             keys = self._component[item].keys()
    576             keys.sort()
    577             #
    578             # NOTE: these conditional checks should not be hard-coded.
    579             #
    580             print >>ostream, len(keys), item.__name__+" Declarations"
    581             for key in keys:
    582                 self._component[item][key].pprint(ostream)
    583             print >>ostream, ""
    584         #
    585         # Model Order
    586         #
    587         print >>ostream, len(self._declarations),"Declarations:",
    588         for i in range(0,len(self._declarations)):
    589           print >>ostream, self._declarations[i].name,
    590         print >>ostream, ""
    591 
    592 
    593     def display(self, filename=None, ostream=None):
    594         """
    595         Print the Pyomo model in a verbose format.
    596         """
    597         if filename is not None:
    598            OUTPUT=open(filename,"w")
    599            self.display(ostream=OUTPUT)
    600            OUTPUT.close()
    601            return
    602         if ostream is None:
    603            ostream = sys.stdout
    604         print >>ostream, "Model "+self.name
    605         print >>ostream, ""
    606         print >>ostream, "  Variables:"
    607         VAR = self.active_components(Var)
    608         if len(VAR) == 0:
    609             print >>ostream, "    None"
    610         else:
    611             for ndx in VAR:
    612                 VAR[ndx].display(prefix="    ",ostream=ostream)
    613         print >>ostream, ""
    614         print >>ostream, "  Objectives:"
    615         OBJ = self.active_components(Objective)
    616         if len(OBJ) == 0:
    617             print >>ostream, "    None"
    618         else:
    619             for ndx in OBJ:
    620                 OBJ[ndx].display(prefix="    ",ostream=ostream)
    621         print >>ostream, ""
    622         CON = self.active_components(Constraint)
    623         print >>ostream, "  Constraints:"
    624         if len(CON) == 0:
    625             print >>ostream, "    None"
    626         else:
    627             for ndx in CON:
    628                 CON[ndx].display(prefix="    ",ostream=ostream)
    629401
    630402    def to_standard_form(self):
  • coopr.pyomo/trunk/coopr/pyomo/base/__init__.py

    r2844 r2865  
    2626from set_types import *
    2727from misc import *
     28from block import *
    2829from PyomoModel import *
    2930#
  • coopr.pyomo/trunk/coopr/pyomo/base/component.py

    r2843 r2865  
    8181        return self
    8282
     83
    8384class DeveloperError(Exception):
    8485    """
  • coopr.pyomo/trunk/coopr/pyomo/base/constraint.py

    r2826 r2865  
    506506        print >>ostream, "  Size="+str(len(self))
    507507        if None in self._data:
    508            print >>ostream, "%s Value=%s" % (
    509              prefix,
    510              pyutilib.misc.format_io(self._data[None].body())
    511            )
     508            if self._data[None].body is None:
     509                val = 'none'
     510            else:
     511                val = pyutilib.misc.format_io(self._data[None].body())
     512            print >>ostream, '%s  Value=%s' % (prefix, val)
    512513        else:
    513514           flag=True
  • coopr.pyomo/trunk/coopr/pyomo/base/indexed_component.py

    r2652 r2865  
     1
     2__all__ = ['IndexedComponent']
    13
    24from component import Component
     
    79
    810    def __init__(self, *args, **kwds):
    9 
    10         # Don't be afraid to pass None, correct 'ctype' can be passed via
    11         # other routes. Error handling now in Component
     11        #
     12        # The default ctype is None, which triggers an error in the
     13        # Component base class.
     14        #
    1215        component_type = kwds.get('ctype', None)
    1316        Component.__init__(self, component_type)
     
    2225                self._index=args[0]
    2326            elif isinstance(args[0],IndexedComponent):
    24                     raise ValueError, "Cannot index a component with a non-set component"
     27                    raise TypeError, "Cannot index a component with a non-set component"
    2528            else:
    2629                try:
  • coopr.pyomo/trunk/coopr/pyomo/base/objective.py

    r2787 r2865  
    226226        print >>ostream, "  Size="+str(len(self))
    227227        if None in self._data:
    228             print >>ostream, '%s  Value=%s' % (
    229               prefix,
    230               pyutilib.misc.format_io(self._data[None].expr(exception=False))
    231             )
     228            if self._data[None].expr is None:
     229                val = 'none'
     230            else:
     231                val = pyutilib.misc.format_io(self._data[None].expr(exception=False))
     232            print >>ostream, '%s  Value=%s' % (prefix, val)
    232233        else:
    233234           for key in self._data:
  • coopr.pyomo/trunk/coopr/pyomo/tests/unit/test_expr.py

    r2422 r2865  
    349349            model.b = Var(model.a)
    350350            self.fail("test_error2")
    351         except ValueError:
     351        except TypeError:
    352352            pass
    353353
     
    606606            model.c = Param(model.b)
    607607            self.fail("Can't index a parameter with a parameter")
    608         except ValueError:
     608        except TypeError:
    609609            pass
    610610        #
  • coopr.pyomo/trunk/coopr/pyomo/tests/unit/varpprint.txt

    r2050 r2865  
    2525   c :  Size=1  Domain=PositiveReals
    2626        Initial Value : Lower Bound : Upper Bound : Current Value: Fixed
    27         2.1 : 0 : None : None : False
     27         2.1 : 0 : None : None : False
    2828   d :  Size=1  Domain=PositiveReals
    2929        Initial Value : Lower Bound : Upper Bound : Current Value: Fixed
    30         3.1 : 0 : None : None : False
     30         3.1 : 0 : None : None : False
    3131   e :  Size=1  Domain=PositiveReals
    3232        Initial Value : Lower Bound : Upper Bound : Current Value: Fixed
    33         4.1 : 0 : None : None : False
     33         4.1 : 0 : None : None : False
    3434
    35352 Objective Declarations
     
    199199                Inf
    200200
     2010 Block Declarations
     202
    20120334 Declarations: a b c d e A B o2 o3_index o3 c1 c2 c3 c4 c5 c6a c6b c7a c7b c8 c9a c9b c10a c10b c11 c15a c15b c16a c16b c12 c13a c13b c14a c14b
  • coopr.pyomo/trunk/examples/pyomo/tutorials/data.out

    r1278 r2865  
    1211210 Constraint Declarations
    122122
     1230 Block Declarations
     124
    12312527 Declarations: A B C D_domain D E_domain E F G_index G H I J Z Y X W U_index U T_index T S R Q P PP O
  • coopr.pyomo/trunk/examples/pyomo/tutorials/param.out

    r1288 r2865  
    75750 Constraint Declarations
    7676
     770 Block Declarations
     78
    777914 Declarations: A B Z Y X_index X W_index W V U T S R_index R
  • coopr.pyomo/trunk/examples/pyomo/tutorials/set.out

    r1265 r2865  
    1161160 Constraint Declarations
    117117
     1180 Block Declarations
     119
    11812028 Declarations: A B C_index C D E F G H Hsub_domain Hsub I J K K_2 L M N_domain N O P_index P R S T U V_index V
  • coopr.pyomo/trunk/examples/pyomo/tutorials/table.out

    r1278 r2865  
    1171170 Constraint Declarations
    118118
     1190 Block Declarations
     120
    11912127 Declarations: A B C D_domain D E_domain E F G_index G H I J Z Y X W U_index U T_index T S R Q P PP O
Note: See TracChangeset for help on using the changeset viewer.