예제 #1
0
    def _apply_to(self, model, **kwds):
        self._preprocess('pao.bilevel.highpoint', model)

        for key, sub in self.submodel.items():
            model.reclassify_component_type(sub, Block)

        setattr(model, 'hpr', create_submodel_hp_block(model))

        model._transformation_data['pao.bilevel.highpoint'].submodel_cuid = \
            ComponentUID(model)
        model._transformation_data['pao.bilevel.highpoint'].block_cuid = \
            ComponentUID(getattr(model, 'hpr'))
예제 #2
0
def EXTERNAL_collect_solution(worker, node_name):
    solution = {}
    tmp = {}
    node = worker.scenario_tree.get_node(node_name)
    scenario = node.scenarios[0]
    stage = node.stage
    instance = scenario.instance
    assert instance is not None
    bySymbol = instance._ScenarioTreeSymbolMap.bySymbol
    for id_ in node._variable_ids:
        # TODO
        #cost_variable_name, cost_variable_index = \
        #    stage._cost_variable
        #stage_cost_obj = instance.find_component(cost_variable_name)\
        #                 [cost_variable_index]
        #if not stage_cost_obj.is_expression():
        #    solution[ComponentUID(stage_cost_obj,cuid_buffer=tmp)] = \
        #        (stage_cost_obj.value, stage_cost_obj.stale)
        for variable_id in node._variable_ids:
            var = bySymbol[variable_id]
            if var.is_expression():
                continue
            solution[ComponentUID(var, cuid_buffer=tmp)] = \
                (var.value, var.stale)

    return solution
예제 #3
0
파일: transform.py 프로젝트: jlgearh/pao
    def _preprocess(self, tname, instance):
        """
        Iterate over the model collecting variable data,
        until all submodels are found.

        """
        var = {}
        for (name, data) in instance.component_map(active=True).items():
            if isinstance(data, Var):
                var[name] = data
            elif isinstance(data, SubModel):
                submodel = data
                if submodel is None:
                    e = "Missing submodel: " + str(name)
                    logger.error(e)
                    raise RuntimeError(e)
                instance._transformation_data[tname].submodel = [name]
                #nest_level = self._nest_level(submodel)
                if submodel._fixed:
                    self._fixed_vardata[name] = [
                        vardata for v in submodel._fixed
                        for vardata in v.values()
                    ]
                    instance._transformation_data[tname].fixed = [
                        ComponentUID(v) for v in self._fixed_vardata[name]
                    ]
                    self._submodel[name] = submodel
                else:
                    e = "Must specify 'fixed' or 'unfixed' options"
                    logger.error(e)
                    raise RuntimeError(e)
                self._preprocess(tname, submodel)
        return
예제 #4
0
def write_nl(model, nl_filename, **kwds):
    """
    Writes a Pyomo model in NL file format and stores
    information about the symbol map that allows it to be
    recovered at a later time for a Pyomo model with
    matching component names.
    """
    symbol_map_filename = nl_filename + ".symbol_map.pickle"

    # write the model and obtain the symbol_map
    _, smap_id = model.write(nl_filename,
                             format=ProblemFormat.nl,
                             io_options=kwds)
    symbol_map = model.solutions.symbol_map[smap_id]

    # save a persistent form of the symbol_map (using pickle) by
    # storing the NL file label with a ComponentUID, which is
    # an efficient lookup code for model components (created
    # by John Siirola)
    tmp_buffer = {}  # this makes the process faster
    symbol_cuid_pairs = tuple(
        (symbol, ComponentUID(var_weakref(), cuid_buffer=tmp_buffer))
        for symbol, var_weakref in symbol_map.bySymbol.items())
    with open(symbol_map_filename, "wb") as f:
        pickle.dump(symbol_cuid_pairs, f)

    return symbol_map_filename
예제 #5
0
파일: highpoint.py 프로젝트: whart222/pao
    def _apply_to(self, model, **kwds):
        submodel_name = kwds.pop('submodel_name', 'hpr')
        self._preprocess('pao.pyomo.highpoint', model)

        map = ComponentMap()
        for key, sub in self.submodel.items():
            model.reclassify_component_type(sub, Block)

        setattr(model, submodel_name, create_submodel_hp_block(model))

        model._transformation_data['pao.pyomo.highpoint'].submodel_cuid = \
            ComponentUID(model)
        model._transformation_data['pao.pyomo.highpoint'].block_cuid = \
            ComponentUID(getattr(model, submodel_name))

        for key, sub in self.submodel.items():
            model.reclassify_component_type(sub, SubModel)
예제 #6
0
 def _sub_transformation(model, sub, key):
     model.reclassify_component_type(sub, Block)
     #
     # Create a block with optimality conditions
     #
     setattr(
         model, key + '_kkt',
         create_submodel_kkt_block(model, sub, deterministic,
                                   self.fixed_vardata[key]))
     model._transformation_data['pao.bilevel.linear_mpec'].submodel_cuid =\
         ComponentUID(sub)
     model._transformation_data['pao.bilevel.linear_mpec'].block_cuid =\
         ComponentUID(getattr(model, key +'_kkt'))
     #
     # Disable the original submodel and
     #
     for data in sub.component_map(active=True).values():
         if not isinstance(data, Var) and not isinstance(data, Set):
             data.deactivate()
예제 #7
0
 def _apply_to(self, model, **kwds):
     deterministic = kwds.pop('deterministic', False)
     submodel_name = kwds.pop('submodel', None)
     #
     # Process options
     #
     submodel = self._preprocess('pao.bilevel.linear_mpec', model, sub=submodel_name)
     model.reclassify_component_type(submodel, Block)
     #
     # Create a block with optimality conditions
     #
     setattr(model, self._submodel+'_kkt',
             create_submodel_kkt_block(model, submodel, deterministic,
                                       self._fixed_vardata))
     model._transformation_data['pao.bilevel.linear_mpec'].submodel_cuid =\
         ComponentUID(submodel)
     model._transformation_data['pao.bilevel.linear_mpec'].block_cuid =\
         ComponentUID(getattr(model, self._submodel+'_kkt'))
     #
     # Disable the original submodel and
     #
     for data in submodel.component_map(active=True).values():
         if not isinstance(data, Var) and not isinstance(data, Set):
             data.deactivate()
예제 #8
0
    def _apply_solver(self):
        start_time = time.time()
        #
        # Cache the instance
        #
        xfrm = TransformationFactory('bilevel.linear_dual')
        xfrm.apply_to(self._instance)
        #
        # Apply an additional transformation to remap bilinear terms
        #
        if self.options.transform is None:
            xfrm = None
        else:
            xfrm = TransformationFactory(self.options.transform)
            xfrm.apply_to(self._instance)
        #
        # Solve with a specified solver
        #
        solver = self.options.solver
        if not self.options.solver:
            solver = 'glpk'

        # use the with block here so that deactivation of the
        # solver plugin always occurs thereby avoiding memory
        # leaks caused by plugins!
        with pyomo.opt.SolverFactory(solver) as opt:
            self.results = []
            #
            # **NOTE: It would be better to override _presolve on the
            #         base class of this solver as you might be
            #         missing a number of keywords that were passed
            #         into the solve method (e.g., none of the
            #         io_options are getting relayed to the subsolver
            #         here).
            #
            self.results.append(
                opt.solve(self._instance,
                          tee=self._tee,
                          timelimit=self._timelimit))
            #
            # Transform the result back into the original model
            #
            tdata = self._instance._transformation_data['bilevel.linear_dual']
            unfixed_cuids = set()
            # Copy variable values and fix them
            for vuid in tdata.fixed:
                for index_, data_ in vuid.find_component_on(
                        self._instance).iteritems():
                    if not data_.fixed:
                        data_.value = self._instance.find_component(
                            data_).value
                        data_.fixed = True
                        unfixed_cuids.add(ComponentUID(data_))
            # Reclassify the SubModel components and resolve
            for name_ in tdata.submodel:
                submodel = getattr(self._instance, name_)
                submodel.activate()
                dual_submodel = getattr(self._instance, name_ + '_dual')
                dual_submodel.deactivate()
                pyomo.util.PyomoAPIFactory(
                    'pyomo.repn.compute_canonical_repn')({}, model=submodel)
                self._instance.reclassify_component_type(name_, Block)
                # use the with block here so that deactivation of the
                # solver plugin always occurs thereby avoiding memory
                # leaks caused by plugins!
                with pyomo.opt.SolverFactory(solver) as opt_inner:
                    #
                    # **NOTE: It would be better to override _presolve on the
                    #         base class of this solver as you might be
                    #         missing a number of keywords that were passed
                    #         into the solve method (e.g., none of the
                    #         io_options are getting relayed to the subsolver
                    #         here).
                    #
                    self.results.append(
                        opt_inner.solve(self._instance,
                                        tee=self._tee,
                                        timelimit=self._timelimit,
                                        select=None))
                    self._instance.solutions.select(0, ignore_fixed_vars=True)
                    data_.parent_component().parent_block(
                    ).reclassify_component_type(name_, SubModel)
            # Unfix variables
            for vuid in tdata.fixed:
                for index_, data_ in vuid.find_component_on(
                        self._instance).iteritems():
                    if ComponentUID(data_) in unfixed_cuids:
                        data_.fixed = False
            stop_time = time.time()
            self.wall_time = stop_time - start_time
            # Reactivate top level objective
            for oname, odata in self._instance.component_map(
                    Objective).items():
                odata.activate()
            #
            # Return the sub-solver return condition value and log
            #
            return pyutilib.misc.Bunch(rc=getattr(opt, '_rc', None),
                                       log=getattr(opt, '_log', None))
예제 #9
0
def get_modified_instance( ph, scenario_tree, scenario_or_bundle, **options):
    # Find the model
    if scenario_tree.contains_bundles():
        model = ph._bundle_binding_instance_map[scenario_or_bundle._name]
    else:
        model = ph._instances[scenario_or_bundle._name]
    b = model.component('_interscenario_plugin')
    if b is not None:
        return model

    #
    # We need to add the interscenario information to this model
    #
    model._interscenario_plugin = b = Block()

    # Save our options
    #
    b.epsilon     = options.pop('epsilon')
    b.cut_scale   = options.pop('cut_scale')
    b.allow_slack = options.pop('allow_slack')
    b.enable_rho  = options.pop('enable_rho')
    b.enable_cuts = options.pop('enable_cuts')
    assert( len(options) == 0 )

    # Information for generating cuts
    #
    b.cutlist = ConstraintList()
    b.abs_int_vars = VarList(within=NonNegativeIntegers)
    b.abs_binary_vars = VarList(within=Binary)

    # Note: the var_ids are on the ORIGINAL scenario models
    rootNode = scenario_tree.findRootNode()
    var_ids = list(iterkeys(rootNode._variable_datas))

    # Right now, this is hard-coded for 2-stage problems - so we only
    # need to worry about the variables from the root node.  These
    # variables should exist on all scenarios.  Set up a (trivial)
    # equality constraint for each variable:
    #    var == current_value{param} + separation_variable{var, fixed=0}
    b.STAGE1VAR = _S1V = Set(initialize=var_ids)
    b.separation_variables = _sep = Var( _S1V, dense=True )
    b.fixed_variable_values = _param = Param(_S1V, mutable=True, initialize=0)

    b.rho = weakref.ref(model.component('PHRHO_%s' % rootNode._name))
    b.weights = weakref.ref(model.component('PHWEIGHT_%s' % rootNode._name))

    if b.allow_slack:
        for idx in _sep:
            _sep[idx].setlb(-b.epsilon)
            _sep[idx].setub(b.epsilon)
    else:
        _sep.fix(0)

    _cuidBuffer = {}
    _src = b.local_stage1_varmap = {}
    for i in _S1V:
        # Note indexing: for each 1st stage var, pick an arbitrary
        # (first) scenario and return the variable (and not it's
        # probability)
        _cuid = ComponentUID(rootNode._variable_datas[i][0][0], _cuidBuffer)
        _src[i] = weakref.ref(_cuid.find_component_on(model))
        #_base_src[i] = weakref.ref(_cuid.find_component_on(base_model))

    def _set_var_value(b, i):
        return _param[i] + _sep[i] - _src[i]() == 0
    b.fixed_variables_constraint \
        = _con = Constraint( _S1V, rule=_set_var_value )

    #
    # TODO: When we get the duals of the first-stage variables, do we
    # want the dual WRT the original objective, or the dual WRT the
    # augmented objective?
    #
    # Move the objective to a standardized place so we can easily find it later
    if PYOMO_4_0:
        _orig_objective = list( x[2] for x in model.all_component_data(
                Objective, active=True, descend_into=True ) )
    else:
        _orig_objective = list( model.component_data_objects(
                Objective, active=True, descend_into=True ) )
    assert(len(_orig_objective) == 1)
    _orig_objective = _orig_objective[0]
    b.original_obj = weakref.ref(_orig_objective)

    # add (and deactivate) the objective for the infeasibility
    # separation problem.
    b.separation_obj = Objective(
        expr= sum( _sep[i]**2 for i in var_ids ),
        sense = minimize )

    # Make sure we get dual information
    if 'dual' not in model:
        # Export and import floating point data
        model.dual = Suffix(direction=Suffix.IMPORT_EXPORT)
    #if 'rc' not in model:
    #    model.rc = Suffix(direction=Suffix.IMPORT_EXPORT)

    if FALLBACK_ON_BRUTE_FORCE_PREPROCESS:
        model.preprocess()
    else:
        _map = {}
        preprocess_block_constraints(b, idMap=_map)

    # Note: we wait to deactivate the objective until after we
    # preprocess so that the obective is correctly processed.
    b.separation_obj.deactivate()
    # (temporarily) deactivate the fixed stage-1 variables
    _con.deactivate()

    toc("InterScenario plugin: generated modified problem instance")
    return model
예제 #10
0
파일: solver1.py 프로젝트: zsyf102900/pyomo
    def _apply_solver(self):
        start_time = time.time()
        #
        # Cache the instance
        #
        xfrm = TransformationFactory('bilevel.linear_dual')
        xfrm.apply_to(self._instance)
        #
        # Verify whether the objective is linear
        #
        nonlinear = False
        for odata in self._instance.component_objects(Objective, active=True):
            nonlinear = odata.expr.polynomial_degree() != 1
            # Stop after the first objective
            break
        #
        # Apply an additional transformation to remap bilinear terms
        #
        if nonlinear:
            gdp_xfrm = TransformationFactory("gdp.bilinear")
            gdp_xfrm.apply_to(self._instance)
            mip_xfrm = TransformationFactory("gdp.bigm")
            mip_xfrm.apply_to(self._instance,
                              bigM=self.options.get('bigM', 100000))
        #
        # Solve with a specified solver
        #
        solver = self.options.solver
        if not self.options.solver:
            solver = 'glpk'

        # use the with block here so that deactivation of the
        # solver plugin always occurs thereby avoiding memory
        # leaks caused by plugins!
        with pyomo.opt.SolverFactory(solver) as opt:
            self.results = []
            #
            # **NOTE: It would be better to override _presolve on the
            #         base class of this solver as you might be
            #         missing a number of keywords that were passed
            #         into the solve method (e.g., none of the
            #         io_options are getting relayed to the subsolver
            #         here).
            #
            self.results.append(
                opt.solve(self._instance,
                          tee=self._tee,
                          timelimit=self._timelimit))
            #print("POST-SOLVE - BEGIN")
            #self._instance.write("tmp.lp", io_options={"symbolic_solver_labels":True})
            #self._instance.pprint()
            #self._instance.display()
            #print("POST-SOLVE - END")
            #
            # If the problem was bilinear, then reactivate the original data
            #
            if nonlinear:
                i = 0
                for v in self._instance.bilinear_data_.vlist.itervalues():
                    #print(v)
                    #print(v.name)
                    #print(type(v))
                    #print(v.value)
                    if abs(v.value) <= 1e-7:
                        self._instance.bilinear_data_.vlist_boolean[i] = 0
                    else:
                        self._instance.bilinear_data_.vlist_boolean[i] = 1
                    i = i + 1
                #
                self._instance.bilinear_data_.deactivate()
            #
            # Transform the result back into the original model
            #
            tdata = self._instance._transformation_data['bilevel.linear_dual']
            unfixed_cuids = set()
            # Copy variable values and fix them
            for vuid in tdata.fixed:
                for index_, data_ in vuid.find_component_on(
                        self._instance).iteritems():
                    if not data_.fixed:
                        data_.value = self._instance.find_component(
                            data_).value
                        data_.fixed = True
                        unfixed_cuids.add(ComponentUID(data_))
            # Reclassify the SubModel components and resolve
            for name_ in tdata.submodel:
                submodel = getattr(self._instance, name_)
                submodel.activate()
                for (name,
                     data) in submodel.component_map(active=False).items():
                    if not isinstance(data, Var) and not isinstance(data, Set):
                        data.activate()
                dual_submodel = getattr(self._instance, name_ + '_dual')
                dual_submodel.deactivate()
                pyomo.common.PyomoAPIFactory(
                    'pyomo.repn.compute_standard_repn')({}, model=submodel)
                self._instance.reclassify_component_type(name_, Block)
                # use the with block here so that deactivation of the
                # solver plugin always occurs thereby avoiding memory
                # leaks caused by plugins!
                with pyomo.opt.SolverFactory(solver) as opt_inner:
                    #
                    # **NOTE: It would be better to override _presolve on the
                    #         base class of this solver as you might be
                    #         missing a number of keywords that were passed
                    #         into the solve method (e.g., none of the
                    #         io_options are getting relayed to the subsolver
                    #         here).
                    #
                    results = opt_inner.solve(self._instance,
                                              tee=self._tee,
                                              timelimit=self._timelimit)
                    #select=None)
            # Unfix variables
            for vuid in tdata.fixed:
                for index_, data_ in vuid.find_component_on(
                        self._instance).iteritems():
                    if ComponentUID(data_) in unfixed_cuids:
                        data_.fixed = False
            #
            self._instance.solutions.select(0, ignore_fixed_vars=True)
            self.results.append(results)
            #
            stop_time = time.time()
            self.wall_time = stop_time - start_time
            self.results_obj = self._setup_results_obj()
            #
            # Reactivate top level objective
            # and reclassify the submodel
            #
            for oname, odata in self._instance.component_map(
                    Objective).items():
                odata.activate()
            # TODO: rework the Block logic to allow for searching SubModel objects for variables, etc.
            #data_.parent_component().parent_block().reclassify_component_type(name_, SubModel)
            #
            # Return the sub-solver return condition value and log
            #
            return Bunch(rc=getattr(opt, '_rc', None),
                         log=getattr(opt, '_log', None))
예제 #11
0
파일: spsolver.py 프로젝트: zypher22/pyomo
    def solve(self, sp, *args, **kwds):
        """
        Solve a stochastic program.

        Args:
            sp: The stochastic program to solve.
            reference_model: A pyomo model with at least the
                set of non-anticipative variable objects
                that were declared on th e scenario tree of
                the stochastic program. If this keyword is
                changed from its default value of None, the
                non leaf-stage variable values in the
                solution will be stored into the variable
                objects on the reference model. Otherwise,
                the results object that is returned will
                contain a solution dictionary called 'xhat'
                that stores the solution nested by tree node
                name.
            options: Ephemeral solver options that will
                temporarily overwrite any matching options
                currently set for the solver.
            output_solver_log (bool): Stream the solver
                output during the solve.
            *args: Passed to the derived solver class
                (see the _solve_impl method).
            **kwds: Passed to the derived solver class
                (see the _solve_impl method).

        Returns: A results object with information about the solution.
        """

        start = time.time()

        reference_model = kwds.pop('reference_model', None)

        tmp_options = kwds.pop('options', None)
        orig_options = self.options
        if tmp_options is not None:
            self.set_options_to_default()
            for opt in orig_options.user_values():
                self.options[opt.name()] = opt.value(accessValue=False)
            for key, val in tmp_options.items():
                self.options[key] = val

        # reset the _userAccessed flag on all options
        # so we can verify that all set options are used
        # each time
        for key in self.options:
            self.options.get(key)._userAccessed = False

        try:
            if isinstance(sp, EmbeddedSP):
                num_scenarios = "<unknown>"
                num_stages = len(sp.time_stages)
                num_na_variables = 0
                num_na_continuous_variables = 0
                for stage in sp.time_stages[:-1]:
                    for var, derived in sp.stage_to_variables_map[stage]:
                        if not derived:
                            num_na_variables += 1
                            if var.is_continuous():
                                num_na_continuous_variables += 1
            else:
                scenario_tree = sp.scenario_tree

                num_scenarios = len(scenario_tree.scenarios)
                num_stages = len(scenario_tree.stages)
                num_na_variables = 0
                num_na_continuous_variables = 0
                for stage in scenario_tree.stages[:-1]:
                    for tree_node in stage.nodes:
                        num_na_variables += len(
                            tree_node._standard_variable_ids)
                        for id_ in tree_node._standard_variable_ids:
                            if not tree_node.is_variable_discrete(id_):
                                num_na_continuous_variables += 1

            if kwds.get('output_solver_log', False):
                print("\n")
                print("-" * 20)
                print("Problem Statistics".center(20))
                print("-" * 20)
                print("Total number of scenarios.................: %10s" %
                      (num_scenarios))
                if scenario_tree.contains_bundles():
                    print("Total number of scenario bundles..........: %10s" %
                          (len(scenario_tree.bundles)))
                print("Total number of time stages...............: %10s" %
                      (num_stages))
                print("Total number of non-anticipative variables: %10s\n"
                      "                                continuous: %10s\n"
                      "                                  discrete: %10s" %
                      (num_na_variables, num_na_continuous_variables,
                       num_na_variables - num_na_continuous_variables))

            results = self._solve_impl(sp, *args, **kwds)

            stop = time.time()
            results.solver.pysp_time = stop - start
            results.solver.name = self.name
            if (results.status is None) or \
               isinstance(results.status, UndefinedData):
                results.status = results.solver.termination_condition
            results.xhat_loaded = False
            if (reference_model is not None):
                # TODO: node/stage costs
                if results.xhat is not None:
                    xhat = results.xhat
                    for tree_obj_name in xhat:
                        tree_obj_solution = xhat[tree_obj_name]
                        for id_ in tree_obj_solution:
                            var = ComponentUID(id_).\
                                  find_component(reference_model)
                            if not var.is_expression_type():
                                var.value = tree_obj_solution[id_]
                                var.stale = False
                    results.xhat_loaded = True
                del results.xhat

        finally:

            # warn about ignored options
            self.options.check_usage(error=False)

            # reset options (if temporary ones were provided)
            if tmp_options is not None:
                current_options = self.options
                self.set_options_to_default()
                for opt in orig_options.user_values():
                    current = current_options.get(opt.name())
                    self.options[opt.name()] = \
                        opt.value(accessValue=current._userAccessed)

        return results
예제 #12
0
def create_model(n_buses=3,
                 n_snapshots=10,
                 name='small_model',
                 p_min_PV=0.1,
                 co2_constraint=None):
    # The function creates a pypsa model with three generators, namely wind, solar and pv
    # The model will contain the specified number of busses and snapshots
    # Lines are added in a ring

    network = pypsa.Network()

    network.set_snapshots(range(n_snapshots))

    network.add("Carrier", 'ocgt', co2_emissions=1)
    network.add("Carrier", "onwind")
    network.add("Carrier", "offwind")
    network.add("Carrier", "wind")
    network.add("Carrier", "solar")

    #add buses
    for i in range(n_buses):
        network.add("Bus", "My bus {}".format(i), x=i, y=i % 2 + 1)

    #add lines in a ring
    for i in range(n_buses):
        network.add(
            "Link",
            "My line {}".format(i),
            bus0="My bus {}".format(i),
            bus1="My bus {}".format((i + 1) % n_buses),
            p_nom=0,
            p_nom_extendable=True,
            length=1,
            capital_cost=np.random.rand() + 0.1,
        )

    # Add generators
    for i in range(n_buses):
        for gen in ['solar', 'wind', 'ocgt']:
            network.add(
                "Generator",
                "{}{}".format(gen, i),
                bus="My bus {}".format(i),
                p_nom_max=10,
                type=gen,
                carrier=gen,
                p_max_pu=p_min_PV if gen == 'solar' and i % 2 == 0 else 1,
                #p_max_pu = float((np.random.rand()>0.5)*0.8),
                p_nom=0,
                capital_cost=np.random.rand() + 0.1,
                marginal_cost=np.random.rand() * 0.1,
                p_nom_extendable=True)

        network.add("Load",
                    "My load {}".format(i),
                    bus="My bus {}".format(i),
                    p_set=np.random.rand(n_snapshots) * 10)
    if co2_constraint != None:
        network.add("GlobalConstraint",
                    "co2_limit",
                    sense="<=",
                    carrier_attribute="co2_emissions",
                    constant=50)

    # %% Solve pyomo model and add MGA constraint
    network.lopf(formulation="cycles", solver_name='gurobi')
    old_objective_value = network.objective
    model = network.model
    #%%
    MGA_slack = 0.1
    # Add the MGA slack constraint.
    model.mga_constraint = pyomo_env.Constraint(
        expr=model.objective.expr <= (1 + MGA_slack) * old_objective_value)

    # Saving model as .lp file
    _, smap_id = model.write(name + ".lp", )
    # Creating symbol map, such that variables can be maped back from .lp file to pyomo model
    symbol_map = model.solutions.symbol_map[smap_id]
    #%%
    tmp_buffer = {}  # this makes the process faster
    symbol_cuid_pairs = dict(
        (symbol, ComponentUID(var_weakref(), cuid_buffer=tmp_buffer))
        for symbol, var_weakref in symbol_map.bySymbol.items())

    # %% Pickeling variable pairs
    with open(name + '.pickle', 'wb') as handle:
        pickle.dump(symbol_cuid_pairs,
                    handle,
                    protocol=pickle.HIGHEST_PROTOCOL)
예제 #13
0
def get_modified_instance(ph, scenario_tree, scenario_or_bundle, **options):
    # Find the model
    if scenario_tree.contains_bundles():
        model = ph._bundle_binding_instance_map[scenario_or_bundle._name]
    else:
        model = ph._instances[scenario_or_bundle._name]
    b = model.component('_interscenario_plugin')
    if b is not None:
        return model

    #
    # We need to add the interscenario information to this model
    #
    model._interscenario_plugin = b = Block()

    # Save our options
    #
    b.epsilon = options.pop('epsilon')
    b.cut_scale = options.pop('cut_scale')
    b.allow_slack = options.pop('allow_slack')
    b.enable_rho = options.pop('enable_rho')
    b.enable_cuts = options.pop('enable_cuts')
    assert (len(options) == 0)

    # Information for generating cuts
    #
    b.cutlist = ConstraintList()
    b.abs_int_vars = VarList(within=NonNegativeIntegers)
    b.abs_binary_vars = VarList(within=Binary)

    # Note: the var_ids are on the ORIGINAL scenario models
    rootNode = scenario_tree.findRootNode()
    var_ids = list(iterkeys(rootNode._variable_datas))

    # Right now, this is hard-coded for 2-stage problems - so we only
    # need to worry about the variables from the root node.  These
    # variables should exist on all scenarios.  Set up a (trivial)
    # equality constraint for each variable:
    #    var == current_value{param} + separation_variable{var, fixed=0}
    b.STAGE1VAR = _S1V = Set(initialize=var_ids)
    b.separation_variables = _sep = Var(_S1V, dense=True)
    b.fixed_variable_values = _param = Param(_S1V, mutable=True, initialize=0)

    b.rho = weakref.ref(model.component('PHRHO_%s' % rootNode._name))
    b.weights = weakref.ref(model.component('PHWEIGHT_%s' % rootNode._name))

    if b.allow_slack:
        for idx in _sep:
            _sep[idx].setlb(-b.epsilon)
            _sep[idx].setub(b.epsilon)
    else:
        _sep.fix(0)

    _cuidBuffer = {}
    _src = b.local_stage1_varmap = {}
    for i in _S1V:
        # Note indexing: for each 1st stage var, pick an arbitrary
        # (first) scenario and return the variable (and not it's
        # probability)
        _cuid = ComponentUID(rootNode._variable_datas[i][0][0], _cuidBuffer)
        _src[i] = weakref.ref(_cuid.find_component_on(model))
        #_base_src[i] = weakref.ref(_cuid.find_component_on(base_model))

    def _set_var_value(b, i):
        return _param[i] + _sep[i] - _src[i]() == 0
    b.fixed_variables_constraint \
        = _con = Constraint( _S1V, rule=_set_var_value )

    #
    # TODO: When we get the duals of the first-stage variables, do we
    # want the dual WRT the original objective, or the dual WRT the
    # augmented objective?
    #
    # Move the objective to a standardized place so we can easily find it later
    if PYOMO_4_0:
        _orig_objective = list(x[2] for x in model.all_component_data(
            Objective, active=True, descend_into=True))
    else:
        _orig_objective = list(
            model.component_data_objects(Objective,
                                         active=True,
                                         descend_into=True))
    assert (len(_orig_objective) == 1)
    _orig_objective = _orig_objective[0]
    b.original_obj = weakref.ref(_orig_objective)

    # add (and deactivate) the objective for the infeasibility
    # separation problem.
    b.separation_obj = Objective(expr=sum(_sep[i]**2 for i in var_ids),
                                 sense=minimize)

    # Make sure we get dual information
    if 'dual' not in model:
        # Export and import floating point data
        model.dual = Suffix(direction=Suffix.IMPORT_EXPORT)
    #if 'rc' not in model:
    #    model.rc = Suffix(direction=Suffix.IMPORT_EXPORT)

    if FALLBACK_ON_BRUTE_FORCE_PREPROCESS:
        model.preprocess()
    else:
        _map = {}
        preprocess_block_constraints(b, idMap=_map)

    # Note: we wait to deactivate the objective until after we
    # preprocess so that the obective is correctly processed.
    b.separation_obj.deactivate()
    # (temporarily) deactivate the fixed stage-1 variables
    _con.deactivate()

    toc("InterScenario plugin: generated modified problem instance")
    return model
예제 #14
0
파일: spsolver.py 프로젝트: Pyomo/pyomo
    def solve(self, sp, *args, **kwds):
        """
        Solve a stochastic program.

        Args:
            sp: The stochastic program to solve.
            reference_model: A pyomo model with at least the
                set of non-anticipative variable objects
                that were declared on th e scenario tree of
                the stochastic program. If this keyword is
                changed from its default value of None, the
                non leaf-stage variable values in the
                solution will be stored into the variable
                objects on the reference model. Otherwise,
                the results object that is returned will
                contain a solution dictionary called 'xhat'
                that stores the solution nested by tree node
                name.
            options: Ephemeral solver options that will
                temporarily overwrite any matching options
                currently set for the solver.
            output_solver_log (bool): Stream the solver
                output during the solve.
            *args: Passed to the derived solver class
                (see the _solve_impl method).
            **kwds: Passed to the derived solver class
                (see the _solve_impl method).

        Returns: A results object with information about the solution.
        """

        start = time.time()

        reference_model = kwds.pop('reference_model', None)

        tmp_options = kwds.pop('options', None)
        orig_options = self.options
        if tmp_options is not None:
            self.set_options_to_default()
            for opt in orig_options.user_values():
                self.options[opt.name()] = opt.value(accessValue=False)
            for key, val in tmp_options.items():
                self.options[key] = val

        # reset the _userAccessed flag on all options
        # so we can verify that all set options are used
        # each time
        for key in self.options:
            self.options.get(key)._userAccessed = False

        try:
            if isinstance(sp, EmbeddedSP):
                num_scenarios = "<unknown>"
                num_stages = len(sp.time_stages)
                num_na_variables = 0
                num_na_continuous_variables = 0
                for stage in sp.time_stages[:-1]:
                    for var,derived in sp.stage_to_variables_map[stage]:
                        if not derived:
                            num_na_variables += 1
                            if var.is_continuous():
                                num_na_continuous_variables += 1
            else:
                scenario_tree = sp.scenario_tree

                num_scenarios = len(scenario_tree.scenarios)
                num_stages = len(scenario_tree.stages)
                num_na_variables = 0
                num_na_continuous_variables = 0
                for stage in scenario_tree.stages[:-1]:
                    for tree_node in stage.nodes:
                        num_na_variables += len(tree_node._standard_variable_ids)
                        for id_ in tree_node._standard_variable_ids:
                            if not tree_node.is_variable_discrete(id_):
                                num_na_continuous_variables += 1

            if kwds.get('output_solver_log', False):
                print("\n")
                print("-"*20)
                print("Problem Statistics".center(20))
                print("-"*20)
                print("Total number of scenarios.................: %10s"
                      % (num_scenarios))
                if scenario_tree.contains_bundles():
                    print("Total number of scenario bundles..........: %10s"
                          % (len(scenario_tree.bundles)))
                print("Total number of time stages...............: %10s"
                      % (num_stages))
                print("Total number of non-anticipative variables: %10s\n"
                      "                                continuous: %10s\n"
                      "                                  discrete: %10s"
                      % (num_na_variables,
                         num_na_continuous_variables,
                         num_na_variables - num_na_continuous_variables))

            results = self._solve_impl(sp, *args, **kwds)

            stop = time.time()
            results.solver.pysp_time = stop - start
            results.solver.name = self.name
            if (results.status is None) or \
               isinstance(results.status, UndefinedData):
                results.status = results.solver.termination_condition
            results.xhat_loaded = False
            if (reference_model is not None):
                # TODO: node/stage costs
                if results.xhat is not None:
                    xhat = results.xhat
                    for tree_obj_name in xhat:
                        tree_obj_solution = xhat[tree_obj_name]
                        for id_ in tree_obj_solution:
                            var = ComponentUID(id_).\
                                  find_component(reference_model)
                            if not var.is_expression_type():
                                var.value = tree_obj_solution[id_]
                                var.stale = False
                    results.xhat_loaded = True
                del results.xhat

        finally:

            # warn about ignored options
            self.options.check_usage(error=False)

            # reset options (if temporary ones were provided)
            if tmp_options is not None:
                current_options = self.options
                self.set_options_to_default()
                for opt in orig_options.user_values():
                    current = current_options.get(opt.name())
                    self.options[opt.name()] = \
                        opt.value(accessValue=current._userAccessed)

        return results
예제 #15
0
 def job(ref_lst, q_done):
     d = dict()
     for symbol, var_weakref in ref_lst.items():
         d[symbol] = ComponentUID(var_weakref)
     q_done.put(d, block=True)
     return
예제 #16
0
def get_symbol_cuid_pairs_seriel(symbol_map):
    symbol_cuid_pairs = dict(
        (symbol, ComponentUID(var_weakref()))
        for symbol, var_weakref in symbol_map.bySymbol.items())
    return symbol_cuid_pairs