def __init__(self): """ Constructor @ In, None @ Out, None """ KnapsackBase.__init__(self) self.optionalConstraints = { 'consistentConstraintI': True, 'consistentConstraintII': False } self.paramsAuxInfo['available_capitals'] = { 'maxDim': 2, 'options': [[None], ['resources'], ['time_periods'], ['resources', 'time_periods']] } self.paramsAuxInfo['net_present_values'] = { 'maxDim': 1, 'options': [['options']] } self.paramsAuxInfo['costs'] = { 'maxDim': 3, 'options': [['options'], ['options', 'resources'], ['options', 'time_periods'], ['options', 'resources', 'time_periods']] }
def setScenarioData(self): """ Method to setup the scenario data for scenario tree construction @ In, None @ Out, None """ KnapsackBase.setScenarioData(self)
def initialize(self, initDict): """ Mehod to initialize @ In, initDict, dict, dictionary of preprocessed input data { 'Sets':{setName: list of setValues}, 'Parameters':{paramName:{setsIndex:paramValue}} or {paramName:{'None':paramValue}}, 'Settings':{xmlTag:xmlVal}, 'Meta':{paramName:{setIndexName:indexDim}} or {paramName:None}, 'Uncertainties':{paramName:{'scenarios':{scenarioName:{setIndex:uncertaintyVal}}, 'probabilities': [ProbVals]}} } @ Out, None """ KnapsackBase.initialize(self, initDict)
def printSolution(self, model): """ Output optimization solution to screen @ In, model, instance, pyomo optimization model @ Out, outputDict, dict, dictionary stores the outputs """ outputDict = KnapsackBase.printSolution(self, model) msg = "Selected investments include:" logger.info(msg) for item in model.investments: for opt in model.optionsOut[item]: outputName = '__'.join([item, opt]) numSelected = pyomo.value(model.x[item, opt]) outputDict[outputName] = [numSelected] if numSelected == 1: msg = "Investment: " + str(item) + " with option: " + str( opt) + " is selected!" logger.info(msg) outputDict['MaxNPV'] = model.obj() logger.info("Maximum NPV: %16.4f" % (outputDict['MaxNPV'])) # Accessing Duals # In some cases, a solver plugin will raise an exception if it encounters a Suffix type that it does not handle # One should be careful in verifying that Suffix declarations are being handled as expected when switching # to a different solver or solver interface. if self.solver == 'cbc': logger.info("Duals Information for Constraint Capacity:") print("Resources|Time_Periods Capacity_Margin") for const in model.component_objects(pyomo.Constraint, active=True): if const.name == 'constraintCapacity': for index in const: print("{0:20s} {1:10.1f}".format( str(index), model.dual[const[index]])) return outputDict
def addAdditionalParams(self, model): """ Add specific Params for MCKP problems @ In, model, pyomo model instance, pyomo abstract model @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.addAdditionalParams(self, model) return model
def initialize(self, initDict): """ Mehod to initialize @ In, initDict, dict, dictionary of preprocessed input data { 'Sets':{setName: list of setValues}, 'Parameters':{paramName:{setsIndex:paramValue}} or {paramName:{'None':paramValue}}, 'Settings':{xmlTag:xmlVal}, 'Meta':{paramName:{setIndexName:indexDim}} or {paramName:None}, 'Uncertainties':{paramName:{'scenarios':{scenarioName:{setIndex:uncertaintyVal}}, 'probabilities': [ProbVals]}} } @ Out, None """ KnapsackBase.initialize(self, initDict) if 'capitals' not in self.sets.keys(): raise IOError('Set capitals is required for %s problem' % self.name)
def createModel(self): """ This method is used to create pyomo model. @ In, None @ Out, model, pyomo.AbstractModel, abstract pyomo model """ model = KnapsackBase.createModel(self) return model
def addExpressions(self, model): """ Add specific expressions for MultipleKnapsack problems @ In, model, pyomo model instance, pyomo abstract model @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.addExpressions(self, model) return model
def addAdditionalConstraints(self, model): """ Add specific constraints for MultipleKnapsack problems @ In, model, pyomo model instance, pyomo abstract model @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.addAdditionalConstraints(self, model) return model
def addAdditionalSets(self, model): """ Add specific Sets for SingleKnapsack problems @ In, model, pyomo model instance, pyomo abstract model @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.addAdditionalSets(self, model) return model
def addVariables(self, model): """ Add variables for MCKP problems @ In, model, pyomo model instance, pyomo abstract model @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.addVariables(self, model) model.x = pyomo.Var(model.options, domain=pyomo.Binary) return model
def addConstraints(self, model): """ Add specific constraints for MultipleKnapsack problems @ In, model, pyomo model instance, pyomo abstract model @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.addConstraints(self, model) def constraintX(model, i): """ sum of investments over knapsacks should less or equal than bounds """ return (self.lowerBounds[i], sum(model.x[i, m] for m in model.capitals), self.upperBounds[i]) model.constraintX = pyomo.Constraint(model.investments, rule=constraintX) def constraintCapacity(model, m, t): """Knapsacks capacity constraints""" return sum( model.costs[i, t] * model.x[i, m] for i in model.investments) <= model.available_capitals[m, t] model.constraintCapacity = pyomo.Constraint(model.capitals, model.time_periods, rule=constraintCapacity) if self.mandatory is not None: def constraintRegulatory(model, i): """Regulatory constraints, always required projects/investments""" return sum(model.x[i, m] for m in model.capitals) == 1 model.constraintRegulatory = pyomo.Constraint( model.mandatory, rule=constraintRegulatory) if self.uncertainties is not None: def consistentConstraintI(model, i, j): """Constraint for variable y if priority project selection is required""" if i == j: return model.y[i, j] == model.y[j, i] else: return sum( model.x[j, m] for m in model.capitals) + model.y[i, j] - 1 <= sum( model.x[i, m] for m in model.capitals) model.consistentConstraintI = pyomo.Constraint( model.investments, model.investments, rule=consistentConstraintI) return model
def pysp_scenario_tree_model_callback(self): """ scenario tree instance creation callback @ In, None @ Out, treeModel, Instance, pyomo scenario tree model for two stage stochastic programming, extra variables 'y[*,*]' is used to define the priorities of investments """ treeModel = KnapsackBase.pysp_scenario_tree_model_callback(self) secondStage = treeModel.Stages.last() # second Stage treeModel.StageCost[secondStage] = 'secondStageCost' treeModel.StageVariables[secondStage].add('x[*,*]') # treeModel.pprint() return treeModel
def initializeModel(self): """ Initialize the pyomo model parameters for Knapsack problem (SingleKnapsack) @ In, None @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.initializeModel(self) model.net_present_values = pyomo.Param(model.investments, mutable=True) model.available_capitals = pyomo.Param(model.time_periods, mutable=True) model.costs = pyomo.Param(model.investments, model.time_periods, mutable=True) return model
def addConstraints(self, model): """ Add specific constraints for MCKP problems @ In, model, pyomo model instance, pyomo abstract model @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.addConstraints(self, model) # constraint (1d) model.constraintCapacity = pyomo.Constraint( model.resources, model.time_periods, rule=self.constraintCapacity) # constraint (1e) and (1f) # last option of any project will be denoted as "non-selection" option if self.mandatory is not None: model.constraintRegulatory = pyomo.Constraint( model.mandatory, rule=self.constraintRegulatory) # Special handles for required and DoNothing options # The options in input file can include DoNothing, but not required to be selected by optimization # Only the investment added to mandatory will be selected. # constraint to handle 'DoNothing' options --> (1f) if self.nonSelection: model.constraintX = pyomo.Constraint( model.investments, rule=self.constraintXNonSelection) else: model.constraintX = pyomo.Constraint(model.investments, rule=self.constraintX) # constraint for scenario analysis if self.uncertainties is not None: if self.nonSelection: # constraint (1c) --> optional model.consistentConstraintI = pyomo.Constraint( model.investments, model.investments, rule=self.consistentConstraintINonSelection) # constraint (1j) including both non-selection and regulatory mandated options model.consistentConstraintII = pyomo.Constraint( model.investments, model.investmentOption, rule=self.consistentConstraintIINoSelection) else: # constraint (1c) --> optional model.consistentConstraintI = pyomo.Constraint( model.investments, model.investments, rule=self.consistentConstraintI) # constraint (1j) model.consistentConstraintII = pyomo.Constraint( model.investments, model.investmentOption, rule=self.consistentConstraintII) return model
def addVariables(self, model): """ Add variables for SingleKnapsack problems @ In, model, pyomo model instance, pyomo abstract model @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.addVariables(self, model) def boundsExpression(model, i): """ set the bounds for soluion variable x using lowerBounds and upperBounds""" return (self.lowerBounds[i], self.upperBounds[i]) model.x = pyomo.Var(model.investments, domain=pyomo.NonNegativeIntegers, bounds=boundsExpression) return model
def printSolution(self, model): """ Output optimization solution to screen @ In, model, instance, pyomo optimization model @ Out, outputDict, dict, dictionary stores the outputs """ outputDict = KnapsackBase.printSolution(self, model) msg = "Selected investments include:" logger.info(msg) outputDict.update({item: list() for item in model.investments}) outputDict['capitals'] = list(cap for cap in model.capitals) for cap in model.capitals: for item in model.investments: numSelected = pyomo.value(model.x[item, cap]) outputDict[item].append(numSelected) if numSelected == 1: msg = "Investment: " + str( item) + " is selected for capitals: " + str(cap) logger.info(msg) elif numSelected > 1: msg = "Investment: " + str( item) + " is selected with limit " + str( int(numSelected)) + " for capitals " + str(cap) logger.info(msg) logger.info("Maximum NPV: %16.4f" % (model.obj())) outputDict['MaxNPV'] = model.obj() # Accessing Duals # In some cases, a solver plugin will raise an exception if it encounters a Suffix type that it does not handle # One should be careful in verifying that Suffix declarations are being handled as expected when switching # to a different solver or solver interface. if self.solver == 'cbc': logger.info("Duals Information for Constraint Capacity:") print("Capitals|Time_Periods Capacity_Margin") for const in model.component_objects(pyomo.Constraint, active=True): if const.name == 'constraintCapacity': for index in const: print("{0:20s} {1:10.1f}".format( str(index), model.dual[const[index]])) return outputDict
def addConstraints(self, model): """ Add specific constraints for SingleKnapsack problems @ In, model, pyomo model instance, pyomo abstract model @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.addConstraints(self, model) def constraintCapacity(model, t): """Knapsacks capacity constraints""" return sum( model.costs[i, t] * model.x[i] for i in model.investments) <= model.available_capitals[t] model.constraintCapacity = pyomo.Constraint(model.time_periods, rule=constraintCapacity) if self.mandatory is not None: def constraintRegulatory(model, i): """Regulatory constraints, always required projects/investments""" return model.x[i] == 1 model.constraintRegulatory = pyomo.Constraint( model.mandatory, rule=constraintRegulatory) if self.uncertainties is not None: def consistentConstraintI(model, i, j): """Constraint for variable y if priority project selection is required""" if i == j: return model.y[i, j] == model.y[j, i] else: return model.x[j] + model.y[i, j] - 1 <= model.x[i] model.consistentConstraintI = pyomo.Constraint( model.investments, model.investments, rule=consistentConstraintI) return model
def initializeModel(self): """ Initialize the pyomo model parameters for Knapsack problem (MCKP) @ In, None @ Out, model, pyomo model instance, pyomo abstract model """ model = KnapsackBase.initializeModel(self) model.options = pyomo.Set(dimen=2, ordered=True) model.resources = pyomo.Set() model.optionsOut = pyomo.Set(model.investments, initialize=self.optionsOutInit, ordered=True) # Set used for constraint (1j) model.investmentOption = pyomo.Set( dimen=2, initialize=self.investmentOptionInit, ordered=True) model.net_present_values = pyomo.Param(model.options, mutable=True) model.available_capitals = pyomo.Param(model.resources, model.time_periods, mutable=True) model.costs = pyomo.Param(model.options, model.resources, model.time_periods, mutable=True) return model