From a0b9a927e4997b767b267bba19d3598d561c2b8b Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:20:15 -0600 Subject: [PATCH 01/83] Renamed _ArcData -> ArcData --- pyomo/core/base/component.py | 2 +- pyomo/network/arc.py | 13 +++++++++---- 2 files changed, 10 insertions(+), 5 deletions(-) diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 22c2bc4b804..c91167379fd 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -806,7 +806,7 @@ class ComponentData(_ComponentBase): # _GeneralExpressionData, _LogicalConstraintData, # _GeneralLogicalConstraintData, _GeneralObjectiveData, # _ParamData,_GeneralVarData, _GeneralBooleanVarData, _DisjunctionData, - # _ArcData, _PortData, _LinearConstraintData, and + # ArcData, _PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those # constructors as well! def __init__(self, component): diff --git a/pyomo/network/arc.py b/pyomo/network/arc.py index 42b7c6ea075..5e68f181a38 100644 --- a/pyomo/network/arc.py +++ b/pyomo/network/arc.py @@ -52,7 +52,7 @@ def _iterable_to_dict(vals, directed, name): return vals -class _ArcData(ActiveComponentData): +class ArcData(ActiveComponentData): """ This class defines the data for a single Arc @@ -246,6 +246,11 @@ def _validate_ports(self, source, destination, ports): ) +class _ArcData(metaclass=RenamedClass): + __renamed__new_class__ = ArcData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register("Component used for connecting two Ports.") class Arc(ActiveIndexedComponent): """ @@ -267,7 +272,7 @@ class Arc(ActiveIndexedComponent): or a two-member iterable of ports """ - _ComponentDataClass = _ArcData + _ComponentDataClass = ArcData def __new__(cls, *args, **kwds): if cls != Arc: @@ -373,9 +378,9 @@ def _pprint(self): ) -class ScalarArc(_ArcData, Arc): +class ScalarArc(ArcData, Arc): def __init__(self, *args, **kwds): - _ArcData.__init__(self, self) + ArcData.__init__(self, self) Arc.__init__(self, *args, **kwds) self.index = UnindexedComponent_index From 2f3e94039bfffac5da785978b0c7bf8c6aa20c9e Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:31:31 -0600 Subject: [PATCH 02/83] Renamed _BlockData -> BlockData --- pyomo/contrib/appsi/base.py | 12 ++-- pyomo/contrib/appsi/fbbt.py | 6 +- pyomo/contrib/appsi/solvers/cbc.py | 6 +- pyomo/contrib/appsi/solvers/cplex.py | 6 +- pyomo/contrib/appsi/solvers/ipopt.py | 6 +- pyomo/contrib/appsi/solvers/wntr.py | 4 +- pyomo/contrib/appsi/writers/lp_writer.py | 4 +- pyomo/contrib/appsi/writers/nl_writer.py | 4 +- pyomo/contrib/benders/benders_cuts.py | 6 +- pyomo/contrib/cp/interval_var.py | 6 +- .../logical_to_disjunctive_program.py | 4 +- pyomo/contrib/incidence_analysis/interface.py | 6 +- .../contrib/incidence_analysis/scc_solver.py | 4 +- .../tests/test_interface.py | 2 +- pyomo/contrib/latex_printer/latex_printer.py | 6 +- .../piecewise/piecewise_linear_function.py | 6 +- .../piecewise_to_gdp_transformation.py | 4 +- .../pynumero/interfaces/external_grey_box.py | 6 +- pyomo/contrib/solver/base.py | 14 ++-- pyomo/contrib/viewer/report.py | 2 +- pyomo/core/base/block.py | 65 ++++++++++--------- pyomo/core/base/piecewise.py | 6 +- .../plugins/transform/logical_to_linear.py | 4 +- pyomo/core/tests/unit/test_block.py | 14 ++-- pyomo/core/tests/unit/test_component.py | 8 +-- pyomo/core/tests/unit/test_indexed_slice.py | 4 +- pyomo/core/tests/unit/test_suffix.py | 4 +- pyomo/dae/flatten.py | 8 +-- pyomo/gdp/disjunct.py | 8 +-- pyomo/gdp/plugins/gdp_var_mover.py | 2 +- pyomo/gdp/tests/common_tests.py | 10 +-- pyomo/gdp/transformed_disjunct.py | 6 +- pyomo/gdp/util.py | 8 +-- pyomo/mpec/complementarity.py | 4 +- pyomo/opt/base/solvers.py | 8 +-- pyomo/repn/util.py | 4 +- .../solvers/direct_or_persistent_solver.py | 4 +- .../solvers/plugins/solvers/direct_solver.py | 8 +-- pyomo/solvers/plugins/solvers/mosek_direct.py | 2 +- .../plugins/solvers/persistent_solver.py | 8 +-- pyomo/util/report_scaling.py | 8 +-- pyomo/util/slices.py | 2 +- 42 files changed, 156 insertions(+), 153 deletions(-) diff --git a/pyomo/contrib/appsi/base.py b/pyomo/contrib/appsi/base.py index 201e5975ac9..b4ade16a597 100644 --- a/pyomo/contrib/appsi/base.py +++ b/pyomo/contrib/appsi/base.py @@ -25,7 +25,7 @@ from pyomo.core.base.sos import _SOSConstraintData, SOSConstraint from pyomo.core.base.var import _GeneralVarData, Var from pyomo.core.base.param import _ParamData, Param -from pyomo.core.base.block import _BlockData, Block +from pyomo.core.base.block import BlockData, Block from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.common.collections import ComponentMap from .utils.get_objective import get_objective @@ -621,13 +621,13 @@ def __str__(self): return self.name @abc.abstractmethod - def solve(self, model: _BlockData, timer: HierarchicalTimer = None) -> Results: + def solve(self, model: BlockData, timer: HierarchicalTimer = None) -> Results: """ Solve a Pyomo model. Parameters ---------- - model: _BlockData + model: BlockData The Pyomo model to be solved timer: HierarchicalTimer An option timer for reporting timing @@ -811,7 +811,7 @@ def add_constraints(self, cons: List[_GeneralConstraintData]): pass @abc.abstractmethod - def add_block(self, block: _BlockData): + def add_block(self, block: BlockData): pass @abc.abstractmethod @@ -827,7 +827,7 @@ def remove_constraints(self, cons: List[_GeneralConstraintData]): pass @abc.abstractmethod - def remove_block(self, block: _BlockData): + def remove_block(self, block: BlockData): pass @abc.abstractmethod @@ -1529,7 +1529,7 @@ def update(self, timer: HierarchicalTimer = None): class LegacySolverInterface(object): def solve( self, - model: _BlockData, + model: BlockData, tee: bool = False, load_solutions: bool = True, logfile: Optional[str] = None, diff --git a/pyomo/contrib/appsi/fbbt.py b/pyomo/contrib/appsi/fbbt.py index 8b6cc52d2aa..c6bbdb5bf3b 100644 --- a/pyomo/contrib/appsi/fbbt.py +++ b/pyomo/contrib/appsi/fbbt.py @@ -23,7 +23,7 @@ from pyomo.core.base.constraint import _GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.objective import _GeneralObjectiveData, minimize, maximize -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base import SymbolMap, TextLabeler from pyomo.common.errors import InfeasibleConstraintException @@ -275,7 +275,7 @@ def _deactivate_satisfied_cons(self): c.deactivate() def perform_fbbt( - self, model: _BlockData, symbolic_solver_labels: Optional[bool] = None + self, model: BlockData, symbolic_solver_labels: Optional[bool] = None ): if model is not self._model: self.set_instance(model, symbolic_solver_labels=symbolic_solver_labels) @@ -304,7 +304,7 @@ def perform_fbbt( self._deactivate_satisfied_cons() return n_iter - def perform_fbbt_with_seed(self, model: _BlockData, seed_var: _GeneralVarData): + def perform_fbbt_with_seed(self, model: BlockData, seed_var: _GeneralVarData): if model is not self._model: self.set_instance(model) else: diff --git a/pyomo/contrib/appsi/solvers/cbc.py b/pyomo/contrib/appsi/solvers/cbc.py index 7f04ffbfce7..57bbf1b4c21 100644 --- a/pyomo/contrib/appsi/solvers/cbc.py +++ b/pyomo/contrib/appsi/solvers/cbc.py @@ -28,7 +28,7 @@ from typing import Optional, Sequence, NoReturn, List, Mapping from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.constraint import _GeneralConstraintData -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.common.timing import HierarchicalTimer @@ -173,7 +173,7 @@ def add_params(self, params: List[_ParamData]): def add_constraints(self, cons: List[_GeneralConstraintData]): self._writer.add_constraints(cons) - def add_block(self, block: _BlockData): + def add_block(self, block: BlockData): self._writer.add_block(block) def remove_variables(self, variables: List[_GeneralVarData]): @@ -185,7 +185,7 @@ def remove_params(self, params: List[_ParamData]): def remove_constraints(self, cons: List[_GeneralConstraintData]): self._writer.remove_constraints(cons) - def remove_block(self, block: _BlockData): + def remove_block(self, block: BlockData): self._writer.remove_block(block) def set_objective(self, obj: _GeneralObjectiveData): diff --git a/pyomo/contrib/appsi/solvers/cplex.py b/pyomo/contrib/appsi/solvers/cplex.py index 1b7ab5000d2..2e04a979fda 100644 --- a/pyomo/contrib/appsi/solvers/cplex.py +++ b/pyomo/contrib/appsi/solvers/cplex.py @@ -24,7 +24,7 @@ from typing import Optional, Sequence, NoReturn, List, Mapping, Dict from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.constraint import _GeneralConstraintData -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.common.timing import HierarchicalTimer @@ -188,7 +188,7 @@ def add_params(self, params: List[_ParamData]): def add_constraints(self, cons: List[_GeneralConstraintData]): self._writer.add_constraints(cons) - def add_block(self, block: _BlockData): + def add_block(self, block: BlockData): self._writer.add_block(block) def remove_variables(self, variables: List[_GeneralVarData]): @@ -200,7 +200,7 @@ def remove_params(self, params: List[_ParamData]): def remove_constraints(self, cons: List[_GeneralConstraintData]): self._writer.remove_constraints(cons) - def remove_block(self, block: _BlockData): + def remove_block(self, block: BlockData): self._writer.remove_block(block) def set_objective(self, obj: _GeneralObjectiveData): diff --git a/pyomo/contrib/appsi/solvers/ipopt.py b/pyomo/contrib/appsi/solvers/ipopt.py index 54e21d333e5..19ec5f8031c 100644 --- a/pyomo/contrib/appsi/solvers/ipopt.py +++ b/pyomo/contrib/appsi/solvers/ipopt.py @@ -30,7 +30,7 @@ from typing import Optional, Sequence, NoReturn, List, Mapping from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.constraint import _GeneralConstraintData -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.common.timing import HierarchicalTimer @@ -237,7 +237,7 @@ def add_params(self, params: List[_ParamData]): def add_constraints(self, cons: List[_GeneralConstraintData]): self._writer.add_constraints(cons) - def add_block(self, block: _BlockData): + def add_block(self, block: BlockData): self._writer.add_block(block) def remove_variables(self, variables: List[_GeneralVarData]): @@ -249,7 +249,7 @@ def remove_params(self, params: List[_ParamData]): def remove_constraints(self, cons: List[_GeneralConstraintData]): self._writer.remove_constraints(cons) - def remove_block(self, block: _BlockData): + def remove_block(self, block: BlockData): self._writer.remove_block(block) def set_objective(self, obj: _GeneralObjectiveData): diff --git a/pyomo/contrib/appsi/solvers/wntr.py b/pyomo/contrib/appsi/solvers/wntr.py index 00c0598c687..928eda2b514 100644 --- a/pyomo/contrib/appsi/solvers/wntr.py +++ b/pyomo/contrib/appsi/solvers/wntr.py @@ -39,7 +39,7 @@ from pyomo.common.collections import ComponentMap from pyomo.core.expr.numvalue import native_numeric_types from typing import Dict, Optional, List -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.param import _ParamData from pyomo.core.base.constraint import _GeneralConstraintData @@ -178,7 +178,7 @@ def _solve(self, timer: HierarchicalTimer): ) return results - def solve(self, model: _BlockData, timer: HierarchicalTimer = None) -> Results: + def solve(self, model: BlockData, timer: HierarchicalTimer = None) -> Results: StaleFlagManager.mark_all_as_stale() if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() diff --git a/pyomo/contrib/appsi/writers/lp_writer.py b/pyomo/contrib/appsi/writers/lp_writer.py index 9984cb7465d..518be5fac99 100644 --- a/pyomo/contrib/appsi/writers/lp_writer.py +++ b/pyomo/contrib/appsi/writers/lp_writer.py @@ -15,7 +15,7 @@ from pyomo.core.base.constraint import _GeneralConstraintData from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.core.base.sos import _SOSConstraintData -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.repn.standard_repn import generate_standard_repn from pyomo.core.expr.numvalue import value from pyomo.contrib.appsi.base import PersistentBase @@ -167,7 +167,7 @@ def _set_objective(self, obj: _GeneralObjectiveData): cobj.name = cname self._writer.objective = cobj - def write(self, model: _BlockData, filename: str, timer: HierarchicalTimer = None): + def write(self, model: BlockData, filename: str, timer: HierarchicalTimer = None): if timer is None: timer = HierarchicalTimer() if model is not self._model: diff --git a/pyomo/contrib/appsi/writers/nl_writer.py b/pyomo/contrib/appsi/writers/nl_writer.py index bd24a86216a..75b026ab521 100644 --- a/pyomo/contrib/appsi/writers/nl_writer.py +++ b/pyomo/contrib/appsi/writers/nl_writer.py @@ -15,7 +15,7 @@ from pyomo.core.base.constraint import _GeneralConstraintData from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.core.base.sos import _SOSConstraintData -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.repn.standard_repn import generate_standard_repn from pyomo.core.expr.numvalue import value from pyomo.contrib.appsi.base import PersistentBase @@ -232,7 +232,7 @@ def _set_objective(self, obj: _GeneralObjectiveData): cobj.sense = sense self._writer.objective = cobj - def write(self, model: _BlockData, filename: str, timer: HierarchicalTimer = None): + def write(self, model: BlockData, filename: str, timer: HierarchicalTimer = None): if timer is None: timer = HierarchicalTimer() if model is not self._model: diff --git a/pyomo/contrib/benders/benders_cuts.py b/pyomo/contrib/benders/benders_cuts.py index cf96ba26164..0653be55986 100644 --- a/pyomo/contrib/benders/benders_cuts.py +++ b/pyomo/contrib/benders/benders_cuts.py @@ -9,7 +9,7 @@ # This software is distributed under the 3-clause BSD License. # ___________________________________________________________________________ -from pyomo.core.base.block import _BlockData, declare_custom_block +from pyomo.core.base.block import BlockData, declare_custom_block import pyomo.environ as pyo from pyomo.solvers.plugins.solvers.persistent_solver import PersistentSolver from pyomo.core.expr.visitor import identify_variables @@ -166,13 +166,13 @@ def _setup_subproblem(b, root_vars, relax_subproblem_cons): @declare_custom_block(name='BendersCutGenerator') -class BendersCutGeneratorData(_BlockData): +class BendersCutGeneratorData(BlockData): def __init__(self, component): if not mpi4py_available: raise ImportError('BendersCutGenerator requires mpi4py.') if not numpy_available: raise ImportError('BendersCutGenerator requires numpy.') - _BlockData.__init__(self, component) + BlockData.__init__(self, component) self.num_subproblems_by_rank = 0 # np.zeros(self.comm.Get_size()) self.subproblems = list() diff --git a/pyomo/contrib/cp/interval_var.py b/pyomo/contrib/cp/interval_var.py index 953b859ea20..ff11d6e3a9f 100644 --- a/pyomo/contrib/cp/interval_var.py +++ b/pyomo/contrib/cp/interval_var.py @@ -18,7 +18,7 @@ from pyomo.core import Integers, value from pyomo.core.base import Any, ScalarVar, ScalarBooleanVar -from pyomo.core.base.block import _BlockData, Block +from pyomo.core.base.block import BlockData, Block from pyomo.core.base.component import ModelComponentFactory from pyomo.core.base.global_set import UnindexedComponent_index from pyomo.core.base.indexed_component import IndexedComponent, UnindexedComponent_set @@ -87,14 +87,14 @@ def get_associated_interval_var(self): return self.parent_block() -class IntervalVarData(_BlockData): +class IntervalVarData(BlockData): """This class defines the abstract interface for a single interval variable.""" # We will put our four variables on this, and everything else is off limits. _Block_reserved_words = Any def __init__(self, component=None): - _BlockData.__init__(self, component) + BlockData.__init__(self, component) with self._declare_reserved_components(): self.is_present = IntervalVarPresence() diff --git a/pyomo/contrib/cp/transform/logical_to_disjunctive_program.py b/pyomo/contrib/cp/transform/logical_to_disjunctive_program.py index e318e621e88..c29bf3f2675 100644 --- a/pyomo/contrib/cp/transform/logical_to_disjunctive_program.py +++ b/pyomo/contrib/cp/transform/logical_to_disjunctive_program.py @@ -26,7 +26,7 @@ Transformation, NonNegativeIntegers, ) -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base import SortComponents from pyomo.core.util import target_list from pyomo.gdp import Disjunct, Disjunction @@ -73,7 +73,7 @@ def _apply_to(self, model, **kwds): transBlocks = {} visitor = LogicalToDisjunctiveVisitor() for t in targets: - if t.ctype is Block or isinstance(t, _BlockData): + if t.ctype is Block or isinstance(t, BlockData): self._transform_block(t, model, visitor, transBlocks) elif t.ctype is LogicalConstraint: if t.is_indexed(): diff --git a/pyomo/contrib/incidence_analysis/interface.py b/pyomo/contrib/incidence_analysis/interface.py index 50cb84daaf5..b798dafced7 100644 --- a/pyomo/contrib/incidence_analysis/interface.py +++ b/pyomo/contrib/incidence_analysis/interface.py @@ -15,7 +15,7 @@ import enum import textwrap -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base.var import Var from pyomo.core.base.constraint import Constraint from pyomo.core.base.objective import Objective @@ -279,7 +279,7 @@ def __init__(self, model=None, active=True, include_inequality=True, **kwds): self._incidence_graph = None self._variables = None self._constraints = None - elif isinstance(model, _BlockData): + elif isinstance(model, BlockData): self._constraints = [ con for con in model.component_data_objects(Constraint, active=active) @@ -348,7 +348,7 @@ def __init__(self, model=None, active=True, include_inequality=True, **kwds): else: raise TypeError( "Unsupported type for incidence graph. Expected PyomoNLP" - " or _BlockData but got %s." % type(model) + " or BlockData but got %s." % type(model) ) @property diff --git a/pyomo/contrib/incidence_analysis/scc_solver.py b/pyomo/contrib/incidence_analysis/scc_solver.py index 0c59fe8703e..378647c190c 100644 --- a/pyomo/contrib/incidence_analysis/scc_solver.py +++ b/pyomo/contrib/incidence_analysis/scc_solver.py @@ -27,7 +27,7 @@ def generate_strongly_connected_components( constraints, variables=None, include_fixed=False, igraph=None ): - """Yield in order ``_BlockData`` that each contain the variables and + """Yield in order ``BlockData`` that each contain the variables and constraints of a single diagonal block in a block lower triangularization of the incidence matrix of constraints and variables @@ -51,7 +51,7 @@ def generate_strongly_connected_components( Yields ------ - Tuple of ``_BlockData``, list-of-variables + Tuple of ``BlockData``, list-of-variables Blocks containing the variables and constraints of every strongly connected component, in a topological order. The variables are the "input variables" for that block. diff --git a/pyomo/contrib/incidence_analysis/tests/test_interface.py b/pyomo/contrib/incidence_analysis/tests/test_interface.py index 4b77d60d8ba..117e2e53b6d 100644 --- a/pyomo/contrib/incidence_analysis/tests/test_interface.py +++ b/pyomo/contrib/incidence_analysis/tests/test_interface.py @@ -1888,7 +1888,7 @@ def test_block_data_obj(self): self.assertEqual(len(var_dmp.unmatched), 1) self.assertEqual(len(con_dmp.unmatched), 1) - msg = "Unsupported type.*_BlockData" + msg = "Unsupported type.*BlockData" with self.assertRaisesRegex(TypeError, msg): igraph = IncidenceGraphInterface(m.block) diff --git a/pyomo/contrib/latex_printer/latex_printer.py b/pyomo/contrib/latex_printer/latex_printer.py index 0a595dd8e1b..42fc9083953 100644 --- a/pyomo/contrib/latex_printer/latex_printer.py +++ b/pyomo/contrib/latex_printer/latex_printer.py @@ -64,7 +64,7 @@ from pyomo.core.base.external import _PythonCallbackFunctionID from pyomo.core.base.enums import SortComponents -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.repn.util import ExprType @@ -587,7 +587,7 @@ def latex_printer( Parameters ---------- - pyomo_component: _BlockData or Model or Objective or Constraint or Expression + pyomo_component: BlockData or Model or Objective or Constraint or Expression The Pyomo component to be printed latex_component_map: pyomo.common.collections.component_map.ComponentMap @@ -674,7 +674,7 @@ def latex_printer( use_equation_environment = True isSingle = True - elif isinstance(pyomo_component, _BlockData): + elif isinstance(pyomo_component, BlockData): objectives = [ obj for obj in pyomo_component.component_data_objects( diff --git a/pyomo/contrib/piecewise/piecewise_linear_function.py b/pyomo/contrib/piecewise/piecewise_linear_function.py index 66ca02ad125..e92edacc756 100644 --- a/pyomo/contrib/piecewise/piecewise_linear_function.py +++ b/pyomo/contrib/piecewise/piecewise_linear_function.py @@ -20,7 +20,7 @@ PiecewiseLinearExpression, ) from pyomo.core import Any, NonNegativeIntegers, value, Var -from pyomo.core.base.block import _BlockData, Block +from pyomo.core.base.block import BlockData, Block from pyomo.core.base.component import ModelComponentFactory from pyomo.core.base.expression import Expression from pyomo.core.base.global_set import UnindexedComponent_index @@ -36,11 +36,11 @@ logger = logging.getLogger(__name__) -class PiecewiseLinearFunctionData(_BlockData): +class PiecewiseLinearFunctionData(BlockData): _Block_reserved_words = Any def __init__(self, component=None): - _BlockData.__init__(self, component) + BlockData.__init__(self, component) with self._declare_reserved_components(): self._expressions = Expression(NonNegativeIntegers) diff --git a/pyomo/contrib/piecewise/transform/piecewise_to_gdp_transformation.py b/pyomo/contrib/piecewise/transform/piecewise_to_gdp_transformation.py index 2e056c47a15..779bb601c71 100644 --- a/pyomo/contrib/piecewise/transform/piecewise_to_gdp_transformation.py +++ b/pyomo/contrib/piecewise/transform/piecewise_to_gdp_transformation.py @@ -33,7 +33,7 @@ Any, ) from pyomo.core.base import Transformation -from pyomo.core.base.block import _BlockData, Block +from pyomo.core.base.block import BlockData, Block from pyomo.core.util import target_list from pyomo.gdp import Disjunct, Disjunction from pyomo.gdp.util import is_child_of @@ -147,7 +147,7 @@ def _apply_to_impl(self, instance, **kwds): self._transform_piecewise_linear_function( t, config.descend_into_expressions ) - elif t.ctype is Block or isinstance(t, _BlockData): + elif t.ctype is Block or isinstance(t, BlockData): self._transform_block(t, config.descend_into_expressions) elif t.ctype is Constraint: if not config.descend_into_expressions: diff --git a/pyomo/contrib/pynumero/interfaces/external_grey_box.py b/pyomo/contrib/pynumero/interfaces/external_grey_box.py index 7e42f161bee..68e652575cc 100644 --- a/pyomo/contrib/pynumero/interfaces/external_grey_box.py +++ b/pyomo/contrib/pynumero/interfaces/external_grey_box.py @@ -18,7 +18,7 @@ from pyomo.common.log import is_debug_set from pyomo.common.timing import ConstructionTimer from pyomo.core.base import Var, Set, Constraint, value -from pyomo.core.base.block import _BlockData, Block, declare_custom_block +from pyomo.core.base.block import BlockData, Block, declare_custom_block from pyomo.core.base.global_set import UnindexedComponent_index from pyomo.core.base.initializer import Initializer from pyomo.core.base.set import UnindexedComponent_set @@ -316,7 +316,7 @@ def evaluate_jacobian_outputs(self): # -class ExternalGreyBoxBlockData(_BlockData): +class ExternalGreyBoxBlockData(BlockData): def set_external_model(self, external_grey_box_model, inputs=None, outputs=None): """ Parameters @@ -424,7 +424,7 @@ class ScalarExternalGreyBoxBlock(ExternalGreyBoxBlockData, ExternalGreyBoxBlock) def __init__(self, *args, **kwds): ExternalGreyBoxBlockData.__init__(self, component=self) ExternalGreyBoxBlock.__init__(self, *args, **kwds) - # The above inherit from Block and _BlockData, so it's not until here + # The above inherit from Block and BlockData, so it's not until here # that we know it's scalar. So we set the index accordingly. self._index = UnindexedComponent_index diff --git a/pyomo/contrib/solver/base.py b/pyomo/contrib/solver/base.py index 8840265763e..4b7da383a57 100644 --- a/pyomo/contrib/solver/base.py +++ b/pyomo/contrib/solver/base.py @@ -17,7 +17,7 @@ from pyomo.core.base.constraint import _GeneralConstraintData from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.param import _ParamData -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.common.config import document_kwargs_from_configdict, ConfigValue from pyomo.common.errors import ApplicationError @@ -108,13 +108,13 @@ def __str__(self): @document_kwargs_from_configdict(CONFIG) @abc.abstractmethod - def solve(self, model: _BlockData, **kwargs) -> Results: + def solve(self, model: BlockData, **kwargs) -> Results: """ Solve a Pyomo model. Parameters ---------- - model: _BlockData + model: BlockData The Pyomo model to be solved **kwargs Additional keyword arguments (including solver_options - passthrough @@ -182,7 +182,7 @@ class PersistentSolverBase(SolverBase): @document_kwargs_from_configdict(PersistentSolverConfig()) @abc.abstractmethod - def solve(self, model: _BlockData, **kwargs) -> Results: + def solve(self, model: BlockData, **kwargs) -> Results: super().solve(model, kwargs) def is_persistent(self): @@ -300,7 +300,7 @@ def add_constraints(self, cons: List[_GeneralConstraintData]): """ @abc.abstractmethod - def add_block(self, block: _BlockData): + def add_block(self, block: BlockData): """ Add a block to the model """ @@ -324,7 +324,7 @@ def remove_constraints(self, cons: List[_GeneralConstraintData]): """ @abc.abstractmethod - def remove_block(self, block: _BlockData): + def remove_block(self, block: BlockData): """ Remove a block from the model """ @@ -496,7 +496,7 @@ def _solution_handler( def solve( self, - model: _BlockData, + model: BlockData, tee: bool = False, load_solutions: bool = True, logfile: Optional[str] = None, diff --git a/pyomo/contrib/viewer/report.py b/pyomo/contrib/viewer/report.py index f83a53c608d..a1f893bba31 100644 --- a/pyomo/contrib/viewer/report.py +++ b/pyomo/contrib/viewer/report.py @@ -149,7 +149,7 @@ def degrees_of_freedom(blk): Return the degrees of freedom. Args: - blk (Block or _BlockData): Block to count degrees of freedom in + blk (Block or BlockData): Block to count degrees of freedom in Returns: (int): Number of degrees of freedom """ diff --git a/pyomo/core/base/block.py b/pyomo/core/base/block.py index 2918ef78b00..8f4e86fe697 100644 --- a/pyomo/core/base/block.py +++ b/pyomo/core/base/block.py @@ -254,7 +254,7 @@ class _BlockConstruction(object): class PseudoMap(AutoSlots.Mixin): """ This class presents a "mock" dict interface to the internal - _BlockData data structures. We return this object to the + BlockData data structures. We return this object to the user to preserve the historical "{ctype : {name : obj}}" interface without actually regenerating that dict-of-dicts data structure. @@ -487,7 +487,7 @@ def iteritems(self): return self.items() -class _BlockData(ActiveComponentData): +class BlockData(ActiveComponentData): """ This class holds the fundamental block data. """ @@ -537,9 +537,9 @@ def __init__(self, component): # _ctypes: { ctype -> [1st idx, last idx, count] } # _decl: { name -> idx } # _decl_order: list( tuples( obj, next_type_idx ) ) - super(_BlockData, self).__setattr__('_ctypes', {}) - super(_BlockData, self).__setattr__('_decl', {}) - super(_BlockData, self).__setattr__('_decl_order', []) + super(BlockData, self).__setattr__('_ctypes', {}) + super(BlockData, self).__setattr__('_decl', {}) + super(BlockData, self).__setattr__('_decl_order', []) self._private_data = None def __getattr__(self, val) -> Union[Component, IndexedComponent, Any]: @@ -574,7 +574,7 @@ def __setattr__(self, name: str, val: Union[Component, IndexedComponent, Any]): # Other Python objects are added with the standard __setattr__ # method. # - super(_BlockData, self).__setattr__(name, val) + super(BlockData, self).__setattr__(name, val) # # Case 2. The attribute exists and it is a component in the # list of declarations in this block. We will use the @@ -628,11 +628,11 @@ def __setattr__(self, name: str, val: Union[Component, IndexedComponent, Any]): # else: # - # NB: This is important: the _BlockData is either a scalar + # NB: This is important: the BlockData is either a scalar # Block (where _parent and _component are defined) or a # single block within an Indexed Block (where only # _component is defined). Regardless, the - # _BlockData.__init__() method declares these methods and + # BlockData.__init__() method declares these methods and # sets them either to None or a weakref. Thus, we will # never have a problem converting these objects from # weakrefs into Blocks and back (when pickling); the @@ -647,23 +647,23 @@ def __setattr__(self, name: str, val: Union[Component, IndexedComponent, Any]): # return True, this shouldn't be too inefficient. # if name == '_parent': - if val is not None and not isinstance(val(), _BlockData): + if val is not None and not isinstance(val(), BlockData): raise ValueError( "Cannot set the '_parent' attribute of Block '%s' " "to a non-Block object (with type=%s); Did you " "try to create a model component named '_parent'?" % (self.name, type(val)) ) - super(_BlockData, self).__setattr__(name, val) + super(BlockData, self).__setattr__(name, val) elif name == '_component': - if val is not None and not isinstance(val(), _BlockData): + if val is not None and not isinstance(val(), BlockData): raise ValueError( "Cannot set the '_component' attribute of Block '%s' " "to a non-Block object (with type=%s); Did you " "try to create a model component named '_component'?" % (self.name, type(val)) ) - super(_BlockData, self).__setattr__(name, val) + super(BlockData, self).__setattr__(name, val) # # At this point, we should only be seeing non-component data # the user is hanging on the blocks (uncommon) or the @@ -680,7 +680,7 @@ def __setattr__(self, name: str, val: Union[Component, IndexedComponent, Any]): delattr(self, name) self.add_component(name, val) else: - super(_BlockData, self).__setattr__(name, val) + super(BlockData, self).__setattr__(name, val) def __delattr__(self, name): """ @@ -703,7 +703,7 @@ def __delattr__(self, name): # Other Python objects are removed with the standard __detattr__ # method. # - super(_BlockData, self).__delattr__(name) + super(BlockData, self).__delattr__(name) def _compact_decl_storage(self): idxMap = {} @@ -775,11 +775,11 @@ def transfer_attributes_from(self, src): Parameters ---------- - src: _BlockData or dict + src: BlockData or dict The Block or mapping that contains the new attributes to assign to this block. """ - if isinstance(src, _BlockData): + if isinstance(src, BlockData): # There is a special case where assigning a parent block to # this block creates a circular hierarchy if src is self: @@ -788,7 +788,7 @@ def transfer_attributes_from(self, src): while p_block is not None: if p_block is src: raise ValueError( - "_BlockData.transfer_attributes_from(): Cannot set a " + "BlockData.transfer_attributes_from(): Cannot set a " "sub-block (%s) to a parent block (%s): creates a " "circular hierarchy" % (self, src) ) @@ -804,7 +804,7 @@ def transfer_attributes_from(self, src): del_src_comp = lambda x: None else: raise ValueError( - "_BlockData.transfer_attributes_from(): expected a " + "BlockData.transfer_attributes_from(): expected a " "Block or dict; received %s" % (type(src).__name__,) ) @@ -878,7 +878,7 @@ def collect_ctypes(self, active=None, descend_into=True): def model(self): # - # Special case: the "Model" is always the top-level _BlockData, + # Special case: the "Model" is always the top-level BlockData, # so if this is the top-level block, it must be the model # # Also note the interesting and intentional characteristic for @@ -1035,7 +1035,7 @@ def add_component(self, name, val): # is inappropriate here. The correct way to add the attribute # is to delegate the work to the next class up the MRO. # - super(_BlockData, self).__setattr__(name, val) + super(BlockData, self).__setattr__(name, val) # # Update the ctype linked lists # @@ -1106,7 +1106,7 @@ def add_component(self, name, val): # This is tricky: If we are in the middle of # constructing an indexed block, the block component # already has _constructed=True. Now, if the - # _BlockData.__init__() defines any local variables + # BlockData.__init__() defines any local variables # (like pyomo.gdp.Disjunct's indicator_var), name(True) # will fail: this block data exists and has a parent(), # but it has not yet been added to the parent's _data @@ -1194,7 +1194,7 @@ def del_component(self, name_or_object): # Note: 'del self.__dict__[name]' is inappropriate here. The # correct way to add the attribute is to delegate the work to # the next class up the MRO. - super(_BlockData, self).__delattr__(name) + super(BlockData, self).__delattr__(name) def reclassify_component_type( self, name_or_object, new_ctype, preserve_declaration_order=True @@ -1994,6 +1994,11 @@ def private_data(self, scope=None): return self._private_data[scope] +class _BlockData(metaclass=RenamedClass): + __renamed__new_class__ = BlockData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register( "A component that contains one or more model components." ) @@ -2007,7 +2012,7 @@ class Block(ActiveIndexedComponent): is deferred. """ - _ComponentDataClass = _BlockData + _ComponentDataClass = BlockData _private_data_initializers = defaultdict(lambda: dict) @overload @@ -2100,7 +2105,7 @@ def _getitem_when_not_present(self, idx): # components declared by the rule have the opportunity # to be initialized with data from # _BlockConstruction.data as they are transferred over. - if obj is not _block and isinstance(obj, _BlockData): + if obj is not _block and isinstance(obj, BlockData): _block.transfer_attributes_from(obj) finally: if data is not None and _block is not self: @@ -2221,7 +2226,7 @@ def display(self, filename=None, ostream=None, prefix=""): ostream = sys.stdout for key in sorted(self): - _BlockData.display(self[key], filename, ostream, prefix) + BlockData.display(self[key], filename, ostream, prefix) @staticmethod def register_private_data_initializer(initializer, scope=None): @@ -2241,9 +2246,9 @@ def register_private_data_initializer(initializer, scope=None): Block._private_data_initializers[scope] = initializer -class ScalarBlock(_BlockData, Block): +class ScalarBlock(BlockData, Block): def __init__(self, *args, **kwds): - _BlockData.__init__(self, component=self) + BlockData.__init__(self, component=self) Block.__init__(self, *args, **kwds) # Initialize the data dict so that (abstract) attribute # assignment will work. Note that we do not trigger @@ -2266,7 +2271,7 @@ def __init__(self, *args, **kwds): Block.__init__(self, *args, **kwds) @overload - def __getitem__(self, index) -> _BlockData: ... + def __getitem__(self, index) -> BlockData: ... __getitem__ = IndexedComponent.__getitem__ # type: ignore @@ -2325,7 +2330,7 @@ def components_data(block, ctype, sort=None, sort_by_keys=False, sort_by_names=F # Create a Block and record all the default attributes, methods, etc. # These will be assumed to be the set of illegal component names. # -_BlockData._Block_reserved_words = set(dir(Block())) +BlockData._Block_reserved_words = set(dir(Block())) class _IndexedCustomBlockMeta(type): @@ -2376,7 +2381,7 @@ def declare_custom_block(name, new_ctype=None): """Decorator to declare components for a custom block data class >>> @declare_custom_block(name=FooBlock) - ... class FooBlockData(_BlockData): + ... class FooBlockData(BlockData): ... # custom block data class ... pass """ diff --git a/pyomo/core/base/piecewise.py b/pyomo/core/base/piecewise.py index 7817a61b2f2..b15def13ccb 100644 --- a/pyomo/core/base/piecewise.py +++ b/pyomo/core/base/piecewise.py @@ -43,7 +43,7 @@ from pyomo.common.deprecation import deprecation_warning from pyomo.common.numeric_types import value from pyomo.common.timing import ConstructionTimer -from pyomo.core.base.block import Block, _BlockData +from pyomo.core.base.block import Block, BlockData from pyomo.core.base.component import ModelComponentFactory from pyomo.core.base.constraint import Constraint, ConstraintList from pyomo.core.base.sos import SOSConstraint @@ -214,14 +214,14 @@ def _characterize_function(name, tol, f_rule, model, points, *index): return 0, values, False -class _PiecewiseData(_BlockData): +class _PiecewiseData(BlockData): """ This class defines the base class for all linearization and piecewise constraint generators.. """ def __init__(self, parent): - _BlockData.__init__(self, parent) + BlockData.__init__(self, parent) self._constructed = True self._bound_type = None self._domain_pts = None diff --git a/pyomo/core/plugins/transform/logical_to_linear.py b/pyomo/core/plugins/transform/logical_to_linear.py index 7aa541a5fdd..69328032004 100644 --- a/pyomo/core/plugins/transform/logical_to_linear.py +++ b/pyomo/core/plugins/transform/logical_to_linear.py @@ -29,7 +29,7 @@ BooleanVarList, SortComponents, ) -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base.boolean_var import _DeprecatedImplicitAssociatedBinaryVariable from pyomo.core.expr.cnf_walker import to_cnf from pyomo.core.expr import ( @@ -100,7 +100,7 @@ def _apply_to(self, model, **kwds): # the GDP will be solved, and it would be wrong to assume that a GDP # will *necessarily* be solved as an algebraic model. The star # example of not doing so being GDPopt.) - if t.ctype is Block or isinstance(t, _BlockData): + if t.ctype is Block or isinstance(t, BlockData): self._transform_block(t, model, new_var_lists, transBlocks) elif t.ctype is LogicalConstraint: if t.is_indexed(): diff --git a/pyomo/core/tests/unit/test_block.py b/pyomo/core/tests/unit/test_block.py index 71e80d90a73..660f65f1944 100644 --- a/pyomo/core/tests/unit/test_block.py +++ b/pyomo/core/tests/unit/test_block.py @@ -54,7 +54,7 @@ from pyomo.core.base.block import ( ScalarBlock, SubclassOf, - _BlockData, + BlockData, declare_custom_block, ) import pyomo.core.expr as EXPR @@ -851,7 +851,7 @@ class DerivedBlock(ScalarBlock): _Block_reserved_words = None DerivedBlock._Block_reserved_words = ( - set(['a', 'b', 'c']) | _BlockData._Block_reserved_words + set(['a', 'b', 'c']) | BlockData._Block_reserved_words ) m = ConcreteModel() @@ -965,7 +965,7 @@ def __init__(self, *args, **kwds): b.c.d.e = Block() with self.assertRaisesRegex( ValueError, - r'_BlockData.transfer_attributes_from\(\): ' + r'BlockData.transfer_attributes_from\(\): ' r'Cannot set a sub-block \(c.d.e\) to a parent block \(c\):', ): b.c.d.e.transfer_attributes_from(b.c) @@ -974,7 +974,7 @@ def __init__(self, *args, **kwds): b = Block(concrete=True) with self.assertRaisesRegex( ValueError, - r'_BlockData.transfer_attributes_from\(\): expected a Block ' + r'BlockData.transfer_attributes_from\(\): expected a Block ' 'or dict; received str', ): b.transfer_attributes_from('foo') @@ -2977,7 +2977,7 @@ def test_write_exceptions(self): def test_override_pprint(self): @declare_custom_block('TempBlock') - class TempBlockData(_BlockData): + class TempBlockData(BlockData): def pprint(self, ostream=None, verbose=False, prefix=""): ostream.write('Testing pprint of a custom block.') @@ -3052,9 +3052,9 @@ def test_derived_block_construction(self): class ConcreteBlock(Block): pass - class ScalarConcreteBlock(_BlockData, ConcreteBlock): + class ScalarConcreteBlock(BlockData, ConcreteBlock): def __init__(self, *args, **kwds): - _BlockData.__init__(self, component=self) + BlockData.__init__(self, component=self) ConcreteBlock.__init__(self, *args, **kwds) _buf = [] diff --git a/pyomo/core/tests/unit/test_component.py b/pyomo/core/tests/unit/test_component.py index 175c4c47d46..b12db9af047 100644 --- a/pyomo/core/tests/unit/test_component.py +++ b/pyomo/core/tests/unit/test_component.py @@ -66,19 +66,17 @@ def test_getname(self): ) m.b[2]._component = None - self.assertEqual( - m.b[2].getname(fully_qualified=True), "[Unattached _BlockData]" - ) + self.assertEqual(m.b[2].getname(fully_qualified=True), "[Unattached BlockData]") # I think that getname() should do this: # self.assertEqual(m.b[2].c[2,4].getname(fully_qualified=True), - # "[Unattached _BlockData].c[2,4]") + # "[Unattached BlockData].c[2,4]") # but it doesn't match current behavior. I will file a PEP to # propose changing the behavior later and proceed to test # current behavior. self.assertEqual(m.b[2].c[2, 4].getname(fully_qualified=True), "c[2,4]") self.assertEqual( - m.b[2].getname(fully_qualified=False), "[Unattached _BlockData]" + m.b[2].getname(fully_qualified=False), "[Unattached BlockData]" ) self.assertEqual(m.b[2].c[2, 4].getname(fully_qualified=False), "c[2,4]") diff --git a/pyomo/core/tests/unit/test_indexed_slice.py b/pyomo/core/tests/unit/test_indexed_slice.py index babd3f3c46a..40aaad9fec9 100644 --- a/pyomo/core/tests/unit/test_indexed_slice.py +++ b/pyomo/core/tests/unit/test_indexed_slice.py @@ -17,7 +17,7 @@ import pyomo.common.unittest as unittest from pyomo.environ import Var, Block, ConcreteModel, RangeSet, Set, Any -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base.indexed_component_slice import IndexedComponent_slice from pyomo.core.base.set import normalize_index @@ -64,7 +64,7 @@ def tearDown(self): self.m = None def test_simple_getitem(self): - self.assertIsInstance(self.m.b[1, 4], _BlockData) + self.assertIsInstance(self.m.b[1, 4], BlockData) def test_simple_getslice(self): _slicer = self.m.b[:, 4] diff --git a/pyomo/core/tests/unit/test_suffix.py b/pyomo/core/tests/unit/test_suffix.py index d2e861cceb5..9597bad7571 100644 --- a/pyomo/core/tests/unit/test_suffix.py +++ b/pyomo/core/tests/unit/test_suffix.py @@ -1603,7 +1603,7 @@ def test_clone_IndexedBlock(self): self.assertEqual(inst.junk.get(model.b[1]), None) self.assertEqual(inst.junk.get(inst.b[1]), 1.0) - def test_clone_BlockData(self): + def test_cloneBlockData(self): model = ConcreteModel() model.b = Block([1, 2, 3]) model.junk = Suffix() @@ -1761,7 +1761,7 @@ def test_pickle_IndexedBlock(self): self.assertEqual(inst.junk.get(model.b[1]), None) self.assertEqual(inst.junk.get(inst.b[1]), 1.0) - def test_pickle_BlockData(self): + def test_pickleBlockData(self): model = ConcreteModel() model.b = Block([1, 2, 3]) model.junk = Suffix() diff --git a/pyomo/dae/flatten.py b/pyomo/dae/flatten.py index febaf7c10c9..3d90cc443c1 100644 --- a/pyomo/dae/flatten.py +++ b/pyomo/dae/flatten.py @@ -259,7 +259,7 @@ def generate_sliced_components( Parameters ---------- - b: _BlockData + b: BlockData Block whose components will be sliced index_stack: list @@ -267,7 +267,7 @@ def generate_sliced_components( component, that have been sliced. This is necessary to return the sets that have been sliced. - slice_: IndexedComponent_slice or _BlockData + slice_: IndexedComponent_slice or BlockData Slice generated so far. This function will yield extensions to this slice at the current level of the block hierarchy. @@ -443,7 +443,7 @@ def flatten_components_along_sets(m, sets, ctype, indices=None, active=None): Parameters ---------- - m: _BlockData + m: BlockData Block whose components (and their sub-components) will be partitioned @@ -546,7 +546,7 @@ def flatten_dae_components(model, time, ctype, indices=None, active=None): Parameters ---------- - model: _BlockData + model: BlockData Block whose components are partitioned time: Set diff --git a/pyomo/gdp/disjunct.py b/pyomo/gdp/disjunct.py index d6e5fcfec57..e6d8d709425 100644 --- a/pyomo/gdp/disjunct.py +++ b/pyomo/gdp/disjunct.py @@ -41,7 +41,7 @@ ComponentData, ) from pyomo.core.base.global_set import UnindexedComponent_index -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base.misc import apply_indexed_rule from pyomo.core.base.indexed_component import ActiveIndexedComponent from pyomo.core.expr.expr_common import ExpressionType @@ -412,7 +412,7 @@ def process(arg): return (_Initializer.deferred_value, arg) -class _DisjunctData(_BlockData): +class _DisjunctData(BlockData): __autoslot_mappers__ = {'_transformation_block': AutoSlots.weakref_mapper} _Block_reserved_words = set() @@ -424,7 +424,7 @@ def transformation_block(self): ) def __init__(self, component): - _BlockData.__init__(self, component) + BlockData.__init__(self, component) with self._declare_reserved_components(): self.indicator_var = AutoLinkedBooleanVar() self.binary_indicator_var = AutoLinkedBinaryVar(self.indicator_var) @@ -498,7 +498,7 @@ def _activate_without_unfixing_indicator(self): class ScalarDisjunct(_DisjunctData, Disjunct): def __init__(self, *args, **kwds): ## FIXME: This is a HACK to get around a chicken-and-egg issue - ## where _BlockData creates the indicator_var *before* + ## where BlockData creates the indicator_var *before* ## Block.__init__ declares the _defer_construction flag. self._defer_construction = True self._suppress_ctypes = set() diff --git a/pyomo/gdp/plugins/gdp_var_mover.py b/pyomo/gdp/plugins/gdp_var_mover.py index 5402b576368..7b1df0bb68f 100644 --- a/pyomo/gdp/plugins/gdp_var_mover.py +++ b/pyomo/gdp/plugins/gdp_var_mover.py @@ -115,7 +115,7 @@ def _apply_to(self, instance, **kwds): disjunct_component, Block ) # HACK: activate the block, but do not activate the - # _BlockData objects + # BlockData objects super(ActiveIndexedComponent, disjunct_component).activate() # Deactivate all constraints. Note that we only need to diff --git a/pyomo/gdp/tests/common_tests.py b/pyomo/gdp/tests/common_tests.py index 5d0d6f6c21b..e15a7c66d8a 100644 --- a/pyomo/gdp/tests/common_tests.py +++ b/pyomo/gdp/tests/common_tests.py @@ -30,7 +30,7 @@ from pyomo.gdp import Disjunct, Disjunction, GDP_Error from pyomo.core.expr.compare import assertExpressionsEqual from pyomo.core.base import constraint, ComponentUID -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.repn import generate_standard_repn import pyomo.core.expr as EXPR import pyomo.gdp.tests.models as models @@ -1704,10 +1704,10 @@ def check_all_components_transformed(self, m): # makeNestedDisjunctions_NestedDisjuncts model. self.assertIsInstance(m.disj.algebraic_constraint, Constraint) self.assertIsInstance(m.d1.disj2.algebraic_constraint, Constraint) - self.assertIsInstance(m.d1.transformation_block, _BlockData) - self.assertIsInstance(m.d2.transformation_block, _BlockData) - self.assertIsInstance(m.d1.d3.transformation_block, _BlockData) - self.assertIsInstance(m.d1.d4.transformation_block, _BlockData) + self.assertIsInstance(m.d1.transformation_block, BlockData) + self.assertIsInstance(m.d2.transformation_block, BlockData) + self.assertIsInstance(m.d1.d3.transformation_block, BlockData) + self.assertIsInstance(m.d1.d4.transformation_block, BlockData) def check_transformation_blocks_nestedDisjunctions(self, m, transformation): diff --git a/pyomo/gdp/transformed_disjunct.py b/pyomo/gdp/transformed_disjunct.py index 6cf60abf414..287d5ed1652 100644 --- a/pyomo/gdp/transformed_disjunct.py +++ b/pyomo/gdp/transformed_disjunct.py @@ -10,11 +10,11 @@ # ___________________________________________________________________________ from pyomo.common.autoslots import AutoSlots -from pyomo.core.base.block import _BlockData, IndexedBlock +from pyomo.core.base.block import BlockData, IndexedBlock from pyomo.core.base.global_set import UnindexedComponent_index, UnindexedComponent_set -class _TransformedDisjunctData(_BlockData): +class _TransformedDisjunctData(BlockData): __slots__ = ('_src_disjunct',) __autoslot_mappers__ = {'_src_disjunct': AutoSlots.weakref_mapper} @@ -23,7 +23,7 @@ def src_disjunct(self): return None if self._src_disjunct is None else self._src_disjunct() def __init__(self, component): - _BlockData.__init__(self, component) + BlockData.__init__(self, component) # pointer to the Disjunct whose transformation block this is. self._src_disjunct = None diff --git a/pyomo/gdp/util.py b/pyomo/gdp/util.py index fe11975954d..55d273938c5 100644 --- a/pyomo/gdp/util.py +++ b/pyomo/gdp/util.py @@ -22,7 +22,7 @@ LogicalConstraint, value, ) -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.common.collections import ComponentMap, ComponentSet, OrderedSet from pyomo.opt import TerminationCondition, SolverStatus @@ -330,7 +330,7 @@ def get_gdp_tree(targets, instance, knownBlocks=None): "Target '%s' is not a component on instance " "'%s'!" % (t.name, instance.name) ) - if t.ctype is Block or isinstance(t, _BlockData): + if t.ctype is Block or isinstance(t, BlockData): _blocks = t.values() if t.is_indexed() else (t,) for block in _blocks: if not block.active: @@ -387,7 +387,7 @@ def is_child_of(parent, child, knownBlocks=None): if knownBlocks is None: knownBlocks = {} tmp = set() - node = child if isinstance(child, (Block, _BlockData)) else child.parent_block() + node = child if isinstance(child, (Block, BlockData)) else child.parent_block() while True: known = knownBlocks.get(node) if known: @@ -452,7 +452,7 @@ def get_src_disjunct(transBlock): Parameters ---------- - transBlock: _BlockData which is in the relaxedDisjuncts IndexedBlock + transBlock: BlockData which is in the relaxedDisjuncts IndexedBlock on a transformation block. """ if ( diff --git a/pyomo/mpec/complementarity.py b/pyomo/mpec/complementarity.py index 79f76a9fc34..3982c7a87ba 100644 --- a/pyomo/mpec/complementarity.py +++ b/pyomo/mpec/complementarity.py @@ -19,7 +19,7 @@ from pyomo.core import Constraint, Var, Block, Set from pyomo.core.base.component import ModelComponentFactory from pyomo.core.base.global_set import UnindexedComponent_index -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.base.disable_methods import disable_methods from pyomo.core.base.initializer import ( Initializer, @@ -43,7 +43,7 @@ def complements(a, b): return ComplementarityTuple(a, b) -class _ComplementarityData(_BlockData): +class _ComplementarityData(BlockData): def _canonical_expression(self, e): # Note: as the complimentarity component maintains references to # the original expression (e), it is NOT safe or valid to bypass diff --git a/pyomo/opt/base/solvers.py b/pyomo/opt/base/solvers.py index f1f9d653a8a..c0698165603 100644 --- a/pyomo/opt/base/solvers.py +++ b/pyomo/opt/base/solvers.py @@ -536,15 +536,15 @@ def solve(self, *args, **kwds): # If the inputs are models, then validate that they have been # constructed! Collect suffix names to try and import from solution. # - from pyomo.core.base.block import _BlockData + from pyomo.core.base.block import BlockData import pyomo.core.base.suffix from pyomo.core.kernel.block import IBlock import pyomo.core.kernel.suffix _model = None for arg in args: - if isinstance(arg, (_BlockData, IBlock)): - if isinstance(arg, _BlockData): + if isinstance(arg, (BlockData, IBlock)): + if isinstance(arg, BlockData): if not arg.is_constructed(): raise RuntimeError( "Attempting to solve model=%s with unconstructed " @@ -553,7 +553,7 @@ def solve(self, *args, **kwds): _model = arg # import suffixes must be on the top-level model - if isinstance(arg, _BlockData): + if isinstance(arg, BlockData): model_suffixes = list( name for ( diff --git a/pyomo/repn/util.py b/pyomo/repn/util.py index 49cca32eaf9..b4a21a2108f 100644 --- a/pyomo/repn/util.py +++ b/pyomo/repn/util.py @@ -486,7 +486,7 @@ def categorize_valid_components( Parameters ---------- - model: _BlockData + model: BlockData The model tree to walk active: True or None @@ -507,7 +507,7 @@ def categorize_valid_components( Returns ------- - component_map: Dict[type, List[_BlockData]] + component_map: Dict[type, List[BlockData]] A dict mapping component type to a list of block data objects that contain declared component of that type. diff --git a/pyomo/solvers/plugins/solvers/direct_or_persistent_solver.py b/pyomo/solvers/plugins/solvers/direct_or_persistent_solver.py index c131b8ad10a..de38a0372d0 100644 --- a/pyomo/solvers/plugins/solvers/direct_or_persistent_solver.py +++ b/pyomo/solvers/plugins/solvers/direct_or_persistent_solver.py @@ -10,7 +10,7 @@ # ___________________________________________________________________________ from pyomo.core.base.PyomoModel import Model -from pyomo.core.base.block import Block, _BlockData +from pyomo.core.base.block import Block, BlockData from pyomo.core.kernel.block import IBlock from pyomo.opt.base.solvers import OptSolver from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler @@ -177,7 +177,7 @@ def _postsolve(self): """ This method should be implemented by subclasses.""" def _set_instance(self, model, kwds={}): - if not isinstance(model, (Model, IBlock, Block, _BlockData)): + if not isinstance(model, (Model, IBlock, Block, BlockData)): msg = ( "The problem instance supplied to the {0} plugin " "'_presolve' method must be a Model or a Block".format(type(self)) diff --git a/pyomo/solvers/plugins/solvers/direct_solver.py b/pyomo/solvers/plugins/solvers/direct_solver.py index 3eab658391c..609a81b2018 100644 --- a/pyomo/solvers/plugins/solvers/direct_solver.py +++ b/pyomo/solvers/plugins/solvers/direct_solver.py @@ -15,7 +15,7 @@ from pyomo.solvers.plugins.solvers.direct_or_persistent_solver import ( DirectOrPersistentSolver, ) -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.kernel.block import IBlock from pyomo.core.base.suffix import active_import_suffix_generator from pyomo.core.kernel.suffix import import_suffix_generator @@ -79,8 +79,8 @@ def solve(self, *args, **kwds): # _model = None for arg in args: - if isinstance(arg, (_BlockData, IBlock)): - if isinstance(arg, _BlockData): + if isinstance(arg, (BlockData, IBlock)): + if isinstance(arg, BlockData): if not arg.is_constructed(): raise RuntimeError( "Attempting to solve model=%s with unconstructed " @@ -89,7 +89,7 @@ def solve(self, *args, **kwds): _model = arg # import suffixes must be on the top-level model - if isinstance(arg, _BlockData): + if isinstance(arg, BlockData): model_suffixes = list( name for (name, comp) in active_import_suffix_generator(arg) ) diff --git a/pyomo/solvers/plugins/solvers/mosek_direct.py b/pyomo/solvers/plugins/solvers/mosek_direct.py index 5000a2f35c4..5c07c73b94e 100644 --- a/pyomo/solvers/plugins/solvers/mosek_direct.py +++ b/pyomo/solvers/plugins/solvers/mosek_direct.py @@ -558,7 +558,7 @@ def _add_block(self, block): Parameters ---------- - block: Block (scalar Block or single _BlockData) + block: Block (scalar Block or single BlockData) """ var_seq = tuple( block.component_data_objects( diff --git a/pyomo/solvers/plugins/solvers/persistent_solver.py b/pyomo/solvers/plugins/solvers/persistent_solver.py index 29aa3f2bbf5..d69c050291b 100644 --- a/pyomo/solvers/plugins/solvers/persistent_solver.py +++ b/pyomo/solvers/plugins/solvers/persistent_solver.py @@ -12,7 +12,7 @@ from pyomo.solvers.plugins.solvers.direct_or_persistent_solver import ( DirectOrPersistentSolver, ) -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.core.kernel.block import IBlock from pyomo.core.base.suffix import active_import_suffix_generator from pyomo.core.kernel.suffix import import_suffix_generator @@ -96,7 +96,7 @@ def add_block(self, block): Parameters ---------- - block: Block (scalar Block or single _BlockData) + block: Block (scalar Block or single BlockData) """ if self._pyomo_model is None: @@ -295,7 +295,7 @@ def remove_block(self, block): Parameters ---------- - block: Block (scalar Block or a single _BlockData) + block: Block (scalar Block or a single BlockData) """ # see PR #366 for discussion about handling indexed @@ -455,7 +455,7 @@ def solve(self, *args, **kwds): self.available(exception_flag=True) # Collect suffix names to try and import from solution. - if isinstance(self._pyomo_model, _BlockData): + if isinstance(self._pyomo_model, BlockData): model_suffixes = list( name for (name, comp) in active_import_suffix_generator(self._pyomo_model) diff --git a/pyomo/util/report_scaling.py b/pyomo/util/report_scaling.py index 201319ea92a..5ae28baa715 100644 --- a/pyomo/util/report_scaling.py +++ b/pyomo/util/report_scaling.py @@ -11,7 +11,7 @@ import pyomo.environ as pyo import math -from pyomo.core.base.block import _BlockData +from pyomo.core.base.block import BlockData from pyomo.common.collections import ComponentSet from pyomo.core.base.var import _GeneralVarData from pyomo.contrib.fbbt.fbbt import compute_bounds_on_expr @@ -42,7 +42,7 @@ def _print_var_set(var_set): return s -def _check_var_bounds(m: _BlockData, too_large: float): +def _check_var_bounds(m: BlockData, too_large: float): vars_without_bounds = ComponentSet() vars_with_large_bounds = ComponentSet() for v in m.component_data_objects(pyo.Var, descend_into=True): @@ -90,7 +90,7 @@ def _check_coefficients( def report_scaling( - m: _BlockData, too_large: float = 5e4, too_small: float = 1e-6 + m: BlockData, too_large: float = 5e4, too_small: float = 1e-6 ) -> bool: """ This function logs potentially poorly scaled parts of the model. @@ -107,7 +107,7 @@ def report_scaling( Parameters ---------- - m: _BlockData + m: BlockData The pyomo model or block too_large: float Values above too_large will generate a log entry diff --git a/pyomo/util/slices.py b/pyomo/util/slices.py index 53f6d364219..d85aa3fa926 100644 --- a/pyomo/util/slices.py +++ b/pyomo/util/slices.py @@ -98,7 +98,7 @@ def slice_component_along_sets(comp, sets, context=None): sets: `pyomo.common.collections.ComponentSet` Contains the sets to replace with slices context: `pyomo.core.base.block.Block` or - `pyomo.core.base.block._BlockData` + `pyomo.core.base.block.BlockData` Block below which to search for sets Returns: From c59f91bb1f0d6b94b9e9fb7bbce05ecb6c033c4c Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:32:28 -0600 Subject: [PATCH 03/83] Renamed _BooleanVarData -> BooleanVarData --- pyomo/core/base/__init__.py | 2 +- pyomo/core/base/boolean_var.py | 13 +++++++++---- pyomo/core/base/component.py | 2 +- pyomo/core/plugins/transform/logical_to_linear.py | 4 ++-- 4 files changed, 13 insertions(+), 8 deletions(-) diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 4bbd0c9dc44..98eceb45490 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -60,7 +60,7 @@ from pyomo.core.base.var import Var, _VarData, _GeneralVarData, ScalarVar, VarList from pyomo.core.base.boolean_var import ( BooleanVar, - _BooleanVarData, + BooleanVarData, _GeneralBooleanVarData, BooleanVarList, ScalarBooleanVar, diff --git a/pyomo/core/base/boolean_var.py b/pyomo/core/base/boolean_var.py index 246dcea6214..bf9d6159754 100644 --- a/pyomo/core/base/boolean_var.py +++ b/pyomo/core/base/boolean_var.py @@ -68,7 +68,7 @@ def __setstate__(self, state): self._boolvar = weakref_ref(state) -class _BooleanVarData(ComponentData, BooleanValue): +class BooleanVarData(ComponentData, BooleanValue): """ This class defines the data for a single variable. @@ -177,6 +177,11 @@ def free(self): return self.unfix() +class _BooleanVarData(metaclass=RenamedClass): + __renamed__new_class__ = BooleanVarData + __renamed__version__ = '6.7.2.dev0' + + def _associated_binary_mapper(encode, val): if val is None: return None @@ -189,7 +194,7 @@ def _associated_binary_mapper(encode, val): return val -class _GeneralBooleanVarData(_BooleanVarData): +class _GeneralBooleanVarData(BooleanVarData): """ This class defines the data for a single Boolean variable. @@ -222,7 +227,7 @@ def __init__(self, component=None): # # These lines represent in-lining of the # following constructors: - # - _BooleanVarData + # - BooleanVarData # - ComponentData # - BooleanValue self._component = weakref_ref(component) if (component is not None) else None @@ -390,7 +395,7 @@ def construct(self, data=None): _set.construct() # - # Construct _BooleanVarData objects for all index values + # Construct BooleanVarData objects for all index values # if not self.is_indexed(): self._data[None] = self diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index c91167379fd..0618d6d9d56 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -802,7 +802,7 @@ class ComponentData(_ComponentBase): __autoslot_mappers__ = {'_component': AutoSlots.weakref_mapper} # NOTE: This constructor is in-lined in the constructors for the following - # classes: _BooleanVarData, _ConnectorData, _ConstraintData, + # classes: BooleanVarData, _ConnectorData, _ConstraintData, # _GeneralExpressionData, _LogicalConstraintData, # _GeneralLogicalConstraintData, _GeneralObjectiveData, # _ParamData,_GeneralVarData, _GeneralBooleanVarData, _DisjunctionData, diff --git a/pyomo/core/plugins/transform/logical_to_linear.py b/pyomo/core/plugins/transform/logical_to_linear.py index 69328032004..da69ca113bd 100644 --- a/pyomo/core/plugins/transform/logical_to_linear.py +++ b/pyomo/core/plugins/transform/logical_to_linear.py @@ -285,7 +285,7 @@ class CnfToLinearVisitor(StreamBasedExpressionVisitor): """Convert CNF logical constraint to linear constraints. Expected expression node types: AndExpression, OrExpression, NotExpression, - AtLeastExpression, AtMostExpression, ExactlyExpression, _BooleanVarData + AtLeastExpression, AtMostExpression, ExactlyExpression, BooleanVarData """ @@ -372,7 +372,7 @@ def beforeChild(self, node, child, child_idx): if child.is_expression_type(): return True, None - # Only thing left should be _BooleanVarData + # Only thing left should be BooleanVarData # # TODO: After the expr_multiple_dispatch is merged, this should # be switched to using as_numeric. From 0c72d9faa267b4f02d3d8b11daad3581701fbb99 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:32:28 -0600 Subject: [PATCH 04/83] Renamed _ComplementarityData -> ComplementarityData --- pyomo/mpec/complementarity.py | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/pyomo/mpec/complementarity.py b/pyomo/mpec/complementarity.py index 3982c7a87ba..aa8db922145 100644 --- a/pyomo/mpec/complementarity.py +++ b/pyomo/mpec/complementarity.py @@ -43,7 +43,7 @@ def complements(a, b): return ComplementarityTuple(a, b) -class _ComplementarityData(BlockData): +class ComplementarityData(BlockData): def _canonical_expression(self, e): # Note: as the complimentarity component maintains references to # the original expression (e), it is NOT safe or valid to bypass @@ -179,9 +179,14 @@ def set_value(self, cc): ) +class _ComplementarityData(metaclass=RenamedClass): + __renamed__new_class__ = ComplementarityData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register("Complementarity conditions.") class Complementarity(Block): - _ComponentDataClass = _ComplementarityData + _ComponentDataClass = ComplementarityData def __new__(cls, *args, **kwds): if cls != Complementarity: @@ -298,9 +303,9 @@ def _conditional_block_printer(ostream, idx, data): ) -class ScalarComplementarity(_ComplementarityData, Complementarity): +class ScalarComplementarity(ComplementarityData, Complementarity): def __init__(self, *args, **kwds): - _ComplementarityData.__init__(self, self) + ComplementarityData.__init__(self, self) Complementarity.__init__(self, *args, **kwds) self._data[None] = self self._index = UnindexedComponent_index From e3fe3162f7b314ecdc84834b727fad6148bfa0ba Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:32:59 -0600 Subject: [PATCH 05/83] Renamed _ConnectorData -> ConnectorData --- pyomo/core/base/component.py | 2 +- pyomo/core/base/connector.py | 15 ++++++++++----- pyomo/core/plugins/transform/expand_connectors.py | 4 ++-- pyomo/repn/standard_repn.py | 4 ++-- 4 files changed, 15 insertions(+), 10 deletions(-) diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 0618d6d9d56..244d9b6a8f5 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -802,7 +802,7 @@ class ComponentData(_ComponentBase): __autoslot_mappers__ = {'_component': AutoSlots.weakref_mapper} # NOTE: This constructor is in-lined in the constructors for the following - # classes: BooleanVarData, _ConnectorData, _ConstraintData, + # classes: BooleanVarData, ConnectorData, _ConstraintData, # _GeneralExpressionData, _LogicalConstraintData, # _GeneralLogicalConstraintData, _GeneralObjectiveData, # _ParamData,_GeneralVarData, _GeneralBooleanVarData, _DisjunctionData, diff --git a/pyomo/core/base/connector.py b/pyomo/core/base/connector.py index 435a2c2fccb..e383b52fc11 100644 --- a/pyomo/core/base/connector.py +++ b/pyomo/core/base/connector.py @@ -28,7 +28,7 @@ logger = logging.getLogger('pyomo.core') -class _ConnectorData(ComponentData, NumericValue): +class ConnectorData(ComponentData, NumericValue): """Holds the actual connector information""" __slots__ = ('vars', 'aggregators') @@ -105,6 +105,11 @@ def _iter_vars(self): yield v +class _ConnectorData(metaclass=RenamedClass): + __renamed__new_class__ = ConnectorData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register( "A bundle of variables that can be manipulated together." ) @@ -157,7 +162,7 @@ def __init__(self, *args, **kwd): # IndexedComponent # def _getitem_when_not_present(self, idx): - _conval = self._data[idx] = _ConnectorData(component=self) + _conval = self._data[idx] = ConnectorData(component=self) return _conval def construct(self, data=None): @@ -170,7 +175,7 @@ def construct(self, data=None): timer = ConstructionTimer(self) self._constructed = True # - # Construct _ConnectorData objects for all index values + # Construct ConnectorData objects for all index values # if self.is_indexed(): self._initialize_members(self._index_set) @@ -258,9 +263,9 @@ def _line_generator(k, v): ) -class ScalarConnector(Connector, _ConnectorData): +class ScalarConnector(Connector, ConnectorData): def __init__(self, *args, **kwd): - _ConnectorData.__init__(self, component=self) + ConnectorData.__init__(self, component=self) Connector.__init__(self, *args, **kwd) self._index = UnindexedComponent_index diff --git a/pyomo/core/plugins/transform/expand_connectors.py b/pyomo/core/plugins/transform/expand_connectors.py index 8c02f3e5698..82ec546e593 100644 --- a/pyomo/core/plugins/transform/expand_connectors.py +++ b/pyomo/core/plugins/transform/expand_connectors.py @@ -25,7 +25,7 @@ Var, SortComponents, ) -from pyomo.core.base.connector import _ConnectorData, ScalarConnector +from pyomo.core.base.connector import ConnectorData, ScalarConnector @TransformationFactory.register( @@ -69,7 +69,7 @@ def _apply_to(self, instance, **kwds): # The set of connectors found in the current constraint found = ComponentSet() - connector_types = set([ScalarConnector, _ConnectorData]) + connector_types = set([ScalarConnector, ConnectorData]) for constraint in instance.component_data_objects( Constraint, sort=SortComponents.deterministic ): diff --git a/pyomo/repn/standard_repn.py b/pyomo/repn/standard_repn.py index 8600a8a50f6..455e7bd9444 100644 --- a/pyomo/repn/standard_repn.py +++ b/pyomo/repn/standard_repn.py @@ -1136,7 +1136,7 @@ def _collect_external_fn(exp, multiplier, idMap, compute_values, verbose, quadra EXPR.RangedExpression: _collect_comparison, EXPR.EqualityExpression: _collect_comparison, EXPR.ExternalFunctionExpression: _collect_external_fn, - # _ConnectorData : _collect_linear_connector, + # ConnectorData : _collect_linear_connector, # ScalarConnector : _collect_linear_connector, _ParamData: _collect_const, ScalarParam: _collect_const, @@ -1536,7 +1536,7 @@ def _linear_collect_pow(exp, multiplier, idMap, compute_values, verbose, coef): #EXPR.EqualityExpression : _linear_collect_comparison, #EXPR.ExternalFunctionExpression : _linear_collect_external_fn, ##EXPR.LinearSumExpression : _collect_linear_sum, - ##_ConnectorData : _collect_linear_connector, + ##ConnectorData : _collect_linear_connector, ##ScalarConnector : _collect_linear_connector, ##param._ParamData : _collect_linear_const, ##param.ScalarParam : _collect_linear_const, From d4b72d2b56193ef68589913d9abd7135242609ba Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:36:53 -0600 Subject: [PATCH 06/83] Renamed _ConstraintData -> ConstraintData --- pyomo/contrib/viewer/report.py | 2 +- pyomo/core/base/__init__.py | 2 +- pyomo/core/base/component.py | 2 +- pyomo/core/base/constraint.py | 15 ++++++++++----- pyomo/core/base/logical_constraint.py | 2 +- pyomo/core/base/matrix_constraint.py | 8 ++++---- pyomo/core/beta/dict_objects.py | 4 ++-- pyomo/core/beta/list_objects.py | 4 ++-- pyomo/core/plugins/transform/add_slack_vars.py | 6 +++--- .../core/plugins/transform/equality_transform.py | 4 ++-- pyomo/core/plugins/transform/model.py | 4 ++-- pyomo/core/plugins/transform/scaling.py | 4 ++-- pyomo/core/tests/unit/test_con.py | 2 +- pyomo/gdp/disjunct.py | 2 +- pyomo/gdp/plugins/hull.py | 6 +++--- pyomo/gdp/tests/test_bigm.py | 8 ++++---- pyomo/gdp/util.py | 4 ++-- pyomo/repn/beta/matrix.py | 14 +++++++------- pyomo/repn/plugins/nl_writer.py | 6 +++--- pyomo/repn/plugins/standard_form.py | 4 ++-- pyomo/solvers/plugins/solvers/mosek_persistent.py | 8 ++++---- .../solvers/plugins/solvers/persistent_solver.py | 6 +++--- .../solvers/tests/checks/test_CPLEXPersistent.py | 2 +- .../tests/checks/test_gurobi_persistent.py | 2 +- .../tests/checks/test_xpress_persistent.py | 2 +- pyomo/util/calc_var_value.py | 6 +++--- 26 files changed, 67 insertions(+), 62 deletions(-) diff --git a/pyomo/contrib/viewer/report.py b/pyomo/contrib/viewer/report.py index a1f893bba31..a28e0082212 100644 --- a/pyomo/contrib/viewer/report.py +++ b/pyomo/contrib/viewer/report.py @@ -50,7 +50,7 @@ def get_residual(ui_data, c): values of the constraint body. This function uses the cached values and will not trigger recalculation. If variable values have changed, this may not yield accurate results. - c(_ConstraintData): a constraint or constraint data + c(ConstraintData): a constraint or constraint data Returns: (float) residual """ diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 98eceb45490..9a5337ac2c8 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -70,7 +70,7 @@ simple_constraintlist_rule, ConstraintList, Constraint, - _ConstraintData, + ConstraintData, ) from pyomo.core.base.logical_constraint import ( LogicalConstraint, diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 244d9b6a8f5..7d6fc903632 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -802,7 +802,7 @@ class ComponentData(_ComponentBase): __autoslot_mappers__ = {'_component': AutoSlots.weakref_mapper} # NOTE: This constructor is in-lined in the constructors for the following - # classes: BooleanVarData, ConnectorData, _ConstraintData, + # classes: BooleanVarData, ConnectorData, ConstraintData, # _GeneralExpressionData, _LogicalConstraintData, # _GeneralLogicalConstraintData, _GeneralObjectiveData, # _ParamData,_GeneralVarData, _GeneralBooleanVarData, _DisjunctionData, diff --git a/pyomo/core/base/constraint.py b/pyomo/core/base/constraint.py index fde1160e563..cbae828a459 100644 --- a/pyomo/core/base/constraint.py +++ b/pyomo/core/base/constraint.py @@ -130,7 +130,7 @@ def C_rule(model, i, j): # -class _ConstraintData(ActiveComponentData): +class ConstraintData(ActiveComponentData): """ This class defines the data for a single constraint. @@ -165,7 +165,7 @@ def __init__(self, component=None): # # These lines represent in-lining of the # following constructors: - # - _ConstraintData, + # - ConstraintData, # - ActiveComponentData # - ComponentData self._component = weakref_ref(component) if (component is not None) else None @@ -280,7 +280,12 @@ def get_value(self): raise NotImplementedError -class _GeneralConstraintData(_ConstraintData): +class _ConstraintData(metaclass=RenamedClass): + __renamed__new_class__ = ConstraintData + __renamed__version__ = '6.7.2.dev0' + + +class _GeneralConstraintData(ConstraintData): """ This class defines the data for a single general constraint. @@ -312,7 +317,7 @@ def __init__(self, expr=None, component=None): # # These lines represent in-lining of the # following constructors: - # - _ConstraintData, + # - ConstraintData, # - ActiveComponentData # - ComponentData self._component = weakref_ref(component) if (component is not None) else None @@ -897,7 +902,7 @@ def __init__(self, *args, **kwds): # currently in place). So during initialization only, we will # treat them as "indexed" objects where things like # Constraint.Skip are managed. But after that they will behave - # like _ConstraintData objects where set_value does not handle + # like ConstraintData objects where set_value does not handle # Constraint.Skip but expects a valid expression or None. # @property diff --git a/pyomo/core/base/logical_constraint.py b/pyomo/core/base/logical_constraint.py index f32d727931a..3a7bca75960 100644 --- a/pyomo/core/base/logical_constraint.py +++ b/pyomo/core/base/logical_constraint.py @@ -373,7 +373,7 @@ def display(self, prefix="", ostream=None): # # Checks flags like Constraint.Skip, etc. before actually creating a - # constraint object. Returns the _ConstraintData object when it should be + # constraint object. Returns the ConstraintData object when it should be # added to the _data dict; otherwise, None is returned or an exception # is raised. # diff --git a/pyomo/core/base/matrix_constraint.py b/pyomo/core/base/matrix_constraint.py index adc9742302e..8dac7c3d24b 100644 --- a/pyomo/core/base/matrix_constraint.py +++ b/pyomo/core/base/matrix_constraint.py @@ -19,7 +19,7 @@ from pyomo.core.expr.numvalue import value from pyomo.core.expr.numeric_expr import LinearExpression from pyomo.core.base.component import ModelComponentFactory -from pyomo.core.base.constraint import IndexedConstraint, _ConstraintData +from pyomo.core.base.constraint import IndexedConstraint, ConstraintData from pyomo.repn.standard_repn import StandardRepn from collections.abc import Mapping @@ -28,7 +28,7 @@ logger = logging.getLogger('pyomo.core') -class _MatrixConstraintData(_ConstraintData): +class _MatrixConstraintData(ConstraintData): """ This class defines the data for a single linear constraint derived from a canonical form Ax=b constraint. @@ -104,7 +104,7 @@ def __init__(self, index, component_ref): # # These lines represent in-lining of the # following constructors: - # - _ConstraintData, + # - ConstraintData, # - ActiveComponentData # - ComponentData self._component = component_ref @@ -209,7 +209,7 @@ def index(self): return self._index # - # Abstract Interface (_ConstraintData) + # Abstract Interface (ConstraintData) # @property diff --git a/pyomo/core/beta/dict_objects.py b/pyomo/core/beta/dict_objects.py index a8298b08e63..53d39939db2 100644 --- a/pyomo/core/beta/dict_objects.py +++ b/pyomo/core/beta/dict_objects.py @@ -15,7 +15,7 @@ from pyomo.common.log import is_debug_set from pyomo.core.base.set_types import Any from pyomo.core.base.var import IndexedVar, _VarData -from pyomo.core.base.constraint import IndexedConstraint, _ConstraintData +from pyomo.core.base.constraint import IndexedConstraint, ConstraintData from pyomo.core.base.objective import IndexedObjective, _ObjectiveData from pyomo.core.base.expression import IndexedExpression, _ExpressionData @@ -193,7 +193,7 @@ def __init__(self, *args, **kwds): # Constructor for ComponentDict needs to # go last in order to handle any initialization # iterable as an argument - ComponentDict.__init__(self, _ConstraintData, *args, **kwds) + ComponentDict.__init__(self, ConstraintData, *args, **kwds) class ObjectiveDict(ComponentDict, IndexedObjective): diff --git a/pyomo/core/beta/list_objects.py b/pyomo/core/beta/list_objects.py index f53997fed17..e8b40e6da53 100644 --- a/pyomo/core/beta/list_objects.py +++ b/pyomo/core/beta/list_objects.py @@ -15,7 +15,7 @@ from pyomo.common.log import is_debug_set from pyomo.core.base.set_types import Any from pyomo.core.base.var import IndexedVar, _VarData -from pyomo.core.base.constraint import IndexedConstraint, _ConstraintData +from pyomo.core.base.constraint import IndexedConstraint, ConstraintData from pyomo.core.base.objective import IndexedObjective, _ObjectiveData from pyomo.core.base.expression import IndexedExpression, _ExpressionData @@ -241,7 +241,7 @@ def __init__(self, *args, **kwds): # Constructor for ComponentList needs to # go last in order to handle any initialization # iterable as an argument - ComponentList.__init__(self, _ConstraintData, *args, **kwds) + ComponentList.__init__(self, ConstraintData, *args, **kwds) class XObjectiveList(ComponentList, IndexedObjective): diff --git a/pyomo/core/plugins/transform/add_slack_vars.py b/pyomo/core/plugins/transform/add_slack_vars.py index 6b5096d315c..0007f8de7ad 100644 --- a/pyomo/core/plugins/transform/add_slack_vars.py +++ b/pyomo/core/plugins/transform/add_slack_vars.py @@ -23,7 +23,7 @@ from pyomo.core.plugins.transform.hierarchy import NonIsomorphicTransformation from pyomo.common.config import ConfigBlock, ConfigValue from pyomo.core.base import ComponentUID -from pyomo.core.base.constraint import _ConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.common.deprecation import deprecation_warning @@ -42,7 +42,7 @@ def target_list(x): # [ESJ 07/15/2020] We have to just pass it through because we need the # instance in order to be able to do anything about it... return [x] - elif isinstance(x, (Constraint, _ConstraintData)): + elif isinstance(x, (Constraint, ConstraintData)): return [x] elif hasattr(x, '__iter__'): ans = [] @@ -53,7 +53,7 @@ def target_list(x): deprecation_msg = None # same as above... ans.append(i) - elif isinstance(i, (Constraint, _ConstraintData)): + elif isinstance(i, (Constraint, ConstraintData)): ans.append(i) else: raise ValueError( diff --git a/pyomo/core/plugins/transform/equality_transform.py b/pyomo/core/plugins/transform/equality_transform.py index a1a1b72f146..99291c2227c 100644 --- a/pyomo/core/plugins/transform/equality_transform.py +++ b/pyomo/core/plugins/transform/equality_transform.py @@ -66,7 +66,7 @@ def _create_using(self, model, **kwds): con = equality.__getattribute__(con_name) # - # Get all _ConstraintData objects + # Get all ConstraintData objects # # We need to get the keys ahead of time because we are modifying # con._data on-the-fly. @@ -104,7 +104,7 @@ def _create_using(self, model, **kwds): con.add(ub_name, new_expr) # Since we explicitly `continue` for equality constraints, we - # can safely remove the old _ConstraintData object + # can safely remove the old ConstraintData object del con._data[ndx] return equality.create() diff --git a/pyomo/core/plugins/transform/model.py b/pyomo/core/plugins/transform/model.py index db8376afd29..7ee268a4292 100644 --- a/pyomo/core/plugins/transform/model.py +++ b/pyomo/core/plugins/transform/model.py @@ -55,8 +55,8 @@ def to_standard_form(self): # N.B. Structure hierarchy: # # active_components: {class: {attr_name: object}} - # object -> Constraint: ._data: {ndx: _ConstraintData} - # _ConstraintData: .lower, .body, .upper + # object -> Constraint: ._data: {ndx: ConstraintData} + # ConstraintData: .lower, .body, .upper # # So, altogether, we access a lower bound via # diff --git a/pyomo/core/plugins/transform/scaling.py b/pyomo/core/plugins/transform/scaling.py index ad894b31fde..6b83a2378d1 100644 --- a/pyomo/core/plugins/transform/scaling.py +++ b/pyomo/core/plugins/transform/scaling.py @@ -15,7 +15,7 @@ Var, Constraint, Objective, - _ConstraintData, + ConstraintData, _ObjectiveData, Suffix, value, @@ -197,7 +197,7 @@ def _apply_to(self, model, rename=True): already_scaled.add(id(c)) # perform the constraint/objective scaling and variable sub scaling_factor = component_scaling_factor_map[c] - if isinstance(c, _ConstraintData): + if isinstance(c, ConstraintData): body = scaling_factor * replace_expressions( expr=c.body, substitution_map=variable_substitution_dict, diff --git a/pyomo/core/tests/unit/test_con.py b/pyomo/core/tests/unit/test_con.py index 6ed19c1bcfd..2fa6c24de9c 100644 --- a/pyomo/core/tests/unit/test_con.py +++ b/pyomo/core/tests/unit/test_con.py @@ -1388,7 +1388,7 @@ def test_empty_singleton(self): # Even though we construct a ScalarConstraint, # if it is not initialized that means it is "empty" # and we should encounter errors when trying to access the - # _ConstraintData interface methods until we assign + # ConstraintData interface methods until we assign # something to the constraint. # self.assertEqual(a._constructed, True) diff --git a/pyomo/gdp/disjunct.py b/pyomo/gdp/disjunct.py index e6d8d709425..de021d37547 100644 --- a/pyomo/gdp/disjunct.py +++ b/pyomo/gdp/disjunct.py @@ -542,7 +542,7 @@ def __init__(self, component=None): # # These lines represent in-lining of the # following constructors: - # - _ConstraintData, + # - ConstraintData, # - ActiveComponentData # - ComponentData self._component = weakref_ref(component) if (component is not None) else None diff --git a/pyomo/gdp/plugins/hull.py b/pyomo/gdp/plugins/hull.py index 5b9d2ad08a9..134a3d16d66 100644 --- a/pyomo/gdp/plugins/hull.py +++ b/pyomo/gdp/plugins/hull.py @@ -750,20 +750,20 @@ def _transform_constraint( if obj.is_indexed(): newConstraint.add((name, i, 'eq'), newConsExpr) - # map the _ConstraintDatas (we mapped the container above) + # map the ConstraintDatas (we mapped the container above) constraint_map.transformed_constraints[c].append( newConstraint[name, i, 'eq'] ) constraint_map.src_constraint[newConstraint[name, i, 'eq']] = c else: newConstraint.add((name, 'eq'), newConsExpr) - # map to the _ConstraintData (And yes, for + # map to the ConstraintData (And yes, for # ScalarConstraints, this is overwriting the map to the # container we made above, and that is what I want to # happen. ScalarConstraints will map to lists. For # IndexedConstraints, we can map the container to the # container, but more importantly, we are mapping the - # _ConstraintDatas to each other above) + # ConstraintDatas to each other above) constraint_map.transformed_constraints[c].append( newConstraint[name, 'eq'] ) diff --git a/pyomo/gdp/tests/test_bigm.py b/pyomo/gdp/tests/test_bigm.py index c6ac49f6d36..bf0239d15e0 100644 --- a/pyomo/gdp/tests/test_bigm.py +++ b/pyomo/gdp/tests/test_bigm.py @@ -27,7 +27,7 @@ value, ) from pyomo.gdp import Disjunct, Disjunction, GDP_Error -from pyomo.core.base import constraint, _ConstraintData +from pyomo.core.base import constraint, ConstraintData from pyomo.core.expr.compare import ( assertExpressionsEqual, assertExpressionsStructurallyEqual, @@ -653,14 +653,14 @@ def test_disjunct_and_constraint_maps(self): if src[0]: # equality self.assertEqual(len(transformed), 2) - self.assertIsInstance(transformed[0], _ConstraintData) - self.assertIsInstance(transformed[1], _ConstraintData) + self.assertIsInstance(transformed[0], ConstraintData) + self.assertIsInstance(transformed[1], ConstraintData) self.assertIs(bigm.get_src_constraint(transformed[0]), srcDisjunct.c) self.assertIs(bigm.get_src_constraint(transformed[1]), srcDisjunct.c) else: # >= self.assertEqual(len(transformed), 1) - self.assertIsInstance(transformed[0], _ConstraintData) + self.assertIsInstance(transformed[0], ConstraintData) # check reverse map from the container self.assertIs(bigm.get_src_constraint(transformed[0]), srcDisjunct.c) diff --git a/pyomo/gdp/util.py b/pyomo/gdp/util.py index 55d273938c5..2164671ea16 100644 --- a/pyomo/gdp/util.py +++ b/pyomo/gdp/util.py @@ -525,13 +525,13 @@ def get_transformed_constraints(srcConstraint): Parameters ---------- - srcConstraint: ScalarConstraint or _ConstraintData, which must be in + srcConstraint: ScalarConstraint or ConstraintData, which must be in the subtree of a transformed Disjunct """ if srcConstraint.is_indexed(): raise GDP_Error( "Argument to get_transformed_constraint should be " - "a ScalarConstraint or _ConstraintData. (If you " + "a ScalarConstraint or ConstraintData. (If you " "want the container for all transformed constraints " "from an IndexedDisjunction, this is the parent " "component of a transformed constraint originating " diff --git a/pyomo/repn/beta/matrix.py b/pyomo/repn/beta/matrix.py index 916b0daf755..0201c46eb18 100644 --- a/pyomo/repn/beta/matrix.py +++ b/pyomo/repn/beta/matrix.py @@ -24,7 +24,7 @@ Constraint, IndexedConstraint, ScalarConstraint, - _ConstraintData, + ConstraintData, ) from pyomo.core.expr.numvalue import native_numeric_types from pyomo.repn import generate_standard_repn @@ -247,7 +247,7 @@ def _get_bound(exp): constraint_containers_removed += 1 for constraint, index in constraint_data_to_remove: # Note that this del is not needed: assigning Constraint.Skip - # above removes the _ConstraintData from the _data dict. + # above removes the ConstraintData from the _data dict. # del constraint[index] constraints_removed += 1 for block, constraint in constraint_containers_to_remove: @@ -348,12 +348,12 @@ def _get_bound(exp): ) -# class _LinearConstraintData(_ConstraintData,LinearCanonicalRepn): +# class _LinearConstraintData(ConstraintData,LinearCanonicalRepn): # # This change breaks this class, but it's unclear whether this # is being used... # -class _LinearConstraintData(_ConstraintData): +class _LinearConstraintData(ConstraintData): """ This class defines the data for a single linear constraint in canonical form. @@ -393,7 +393,7 @@ def __init__(self, index, component=None): # # These lines represent in-lining of the # following constructors: - # - _ConstraintData, + # - ConstraintData, # - ActiveComponentData # - ComponentData self._component = weakref_ref(component) if (component is not None) else None @@ -442,7 +442,7 @@ def __init__(self, index, component=None): # These lines represent in-lining of the # following constructors: # - _LinearConstraintData - # - _ConstraintData, + # - ConstraintData, # - ActiveComponentData # - ComponentData self._component = weakref_ref(component) if (component is not None) else None @@ -584,7 +584,7 @@ def constant(self): return sum(terms) # - # Abstract Interface (_ConstraintData) + # Abstract Interface (ConstraintData) # @property diff --git a/pyomo/repn/plugins/nl_writer.py b/pyomo/repn/plugins/nl_writer.py index ee5b65149ae..29d841248da 100644 --- a/pyomo/repn/plugins/nl_writer.py +++ b/pyomo/repn/plugins/nl_writer.py @@ -69,7 +69,7 @@ minimize, ) from pyomo.core.base.component import ActiveComponent -from pyomo.core.base.constraint import _ConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.expression import ScalarExpression, _GeneralExpressionData from pyomo.core.base.objective import ( ScalarObjective, @@ -134,7 +134,7 @@ class NLWriterInfo(object): The list of (unfixed) Pyomo model variables in the order written to the NL file - constraints: List[_ConstraintData] + constraints: List[ConstraintData] The list of (active) Pyomo model constraints in the order written to the NL file @@ -466,7 +466,7 @@ def compile(self, column_order, row_order, obj_order, model_id): self.obj[obj_order[_id]] = val elif _id == model_id: self.prob[0] = val - elif isinstance(obj, (_VarData, _ConstraintData, _ObjectiveData)): + elif isinstance(obj, (_VarData, ConstraintData, _ObjectiveData)): missing_component_data.add(obj) elif isinstance(obj, (Var, Constraint, Objective)): # Expand this indexed component to store the diff --git a/pyomo/repn/plugins/standard_form.py b/pyomo/repn/plugins/standard_form.py index 239cd845930..e6dc217acc9 100644 --- a/pyomo/repn/plugins/standard_form.py +++ b/pyomo/repn/plugins/standard_form.py @@ -76,11 +76,11 @@ class LinearStandardFormInfo(object): The constraint right-hand sides. - rows : List[Tuple[_ConstraintData, int]] + rows : List[Tuple[ConstraintData, int]] The list of Pyomo constraint objects corresponding to the rows in `A`. Each element in the list is a 2-tuple of - (_ConstraintData, row_multiplier). The `row_multiplier` will be + (ConstraintData, row_multiplier). The `row_multiplier` will be +/- 1 indicating if the row was multiplied by -1 (corresponding to a constraint lower bound) or +1 (upper bound). diff --git a/pyomo/solvers/plugins/solvers/mosek_persistent.py b/pyomo/solvers/plugins/solvers/mosek_persistent.py index 97f88e0cb9a..9e7f8de1b41 100644 --- a/pyomo/solvers/plugins/solvers/mosek_persistent.py +++ b/pyomo/solvers/plugins/solvers/mosek_persistent.py @@ -85,7 +85,7 @@ def add_constraints(self, con_seq): Parameters ---------- - con_seq: tuple/list of Constraint (scalar Constraint or single _ConstraintData) + con_seq: tuple/list of Constraint (scalar Constraint or single ConstraintData) """ self._add_constraints(con_seq) @@ -137,7 +137,7 @@ def remove_constraint(self, solver_con): To remove a conic-domain, you should use the remove_block method. Parameters ---------- - solver_con: Constraint (scalar Constraint or single _ConstraintData) + solver_con: Constraint (scalar Constraint or single ConstraintData) """ self.remove_constraints(solver_con) @@ -151,7 +151,7 @@ def remove_constraints(self, *solver_cons): Parameters ---------- - *solver_cons: Constraint (scalar Constraint or single _ConstraintData) + *solver_cons: Constraint (scalar Constraint or single ConstraintData) """ lq_cons = tuple( itertools.filterfalse(lambda x: isinstance(x, _ConicBase), solver_cons) @@ -205,7 +205,7 @@ def update_vars(self, *solver_vars): changing variable types and bounds. Parameters ---------- - *solver_var: Constraint (scalar Constraint or single _ConstraintData) + *solver_var: Constraint (scalar Constraint or single ConstraintData) """ try: var_ids = [] diff --git a/pyomo/solvers/plugins/solvers/persistent_solver.py b/pyomo/solvers/plugins/solvers/persistent_solver.py index d69c050291b..79cd669dd71 100644 --- a/pyomo/solvers/plugins/solvers/persistent_solver.py +++ b/pyomo/solvers/plugins/solvers/persistent_solver.py @@ -132,7 +132,7 @@ def add_constraint(self, con): Parameters ---------- - con: Constraint (scalar Constraint or single _ConstraintData) + con: Constraint (scalar Constraint or single ConstraintData) """ if self._pyomo_model is None: @@ -208,7 +208,7 @@ def add_column(self, model, var, obj_coef, constraints, coefficients): model: pyomo ConcreteModel to which the column will be added var: Var (scalar Var or single _VarData) obj_coef: float, pyo.Param - constraints: list of scalar Constraints of single _ConstraintDatas + constraints: list of scalar Constraints of single ConstraintDatas coefficients: list of the coefficient to put on var in the associated constraint """ @@ -328,7 +328,7 @@ def remove_constraint(self, con): Parameters ---------- - con: Constraint (scalar Constraint or single _ConstraintData) + con: Constraint (scalar Constraint or single ConstraintData) """ # see PR #366 for discussion about handling indexed diff --git a/pyomo/solvers/tests/checks/test_CPLEXPersistent.py b/pyomo/solvers/tests/checks/test_CPLEXPersistent.py index 91a60eee9dd..442212d4fbb 100644 --- a/pyomo/solvers/tests/checks/test_CPLEXPersistent.py +++ b/pyomo/solvers/tests/checks/test_CPLEXPersistent.py @@ -101,7 +101,7 @@ def test_add_column_exceptions(self): # add indexed constraint self.assertRaises(AttributeError, opt.add_column, m, m.y, -2, [m.ci], [1]) - # add something not a _ConstraintData + # add something not a ConstraintData self.assertRaises(AttributeError, opt.add_column, m, m.y, -2, [m.x], [1]) # constraint not on solver model diff --git a/pyomo/solvers/tests/checks/test_gurobi_persistent.py b/pyomo/solvers/tests/checks/test_gurobi_persistent.py index a2c089207e5..812390c23a4 100644 --- a/pyomo/solvers/tests/checks/test_gurobi_persistent.py +++ b/pyomo/solvers/tests/checks/test_gurobi_persistent.py @@ -382,7 +382,7 @@ def test_add_column_exceptions(self): # add indexed constraint self.assertRaises(AttributeError, opt.add_column, m, m.y, -2, [m.ci], [1]) - # add something not a _ConstraintData + # add something not a ConstraintData self.assertRaises(AttributeError, opt.add_column, m, m.y, -2, [m.x], [1]) # constraint not on solver model diff --git a/pyomo/solvers/tests/checks/test_xpress_persistent.py b/pyomo/solvers/tests/checks/test_xpress_persistent.py index ddae860cd92..dcd36780f62 100644 --- a/pyomo/solvers/tests/checks/test_xpress_persistent.py +++ b/pyomo/solvers/tests/checks/test_xpress_persistent.py @@ -262,7 +262,7 @@ def test_add_column_exceptions(self): # add indexed constraint self.assertRaises(AttributeError, opt.add_column, m, m.y, -2, [m.ci], [1]) - # add something not a _ConstraintData + # add something not a ConstraintData self.assertRaises(AttributeError, opt.add_column, m, m.y, -2, [m.x], [1]) # constraint not on solver model diff --git a/pyomo/util/calc_var_value.py b/pyomo/util/calc_var_value.py index b5e620fea07..d5bceb5c67b 100644 --- a/pyomo/util/calc_var_value.py +++ b/pyomo/util/calc_var_value.py @@ -12,7 +12,7 @@ from pyomo.common.errors import IterationLimitError from pyomo.common.numeric_types import native_numeric_types, native_complex_types, value from pyomo.core.expr.calculus.derivatives import differentiate -from pyomo.core.base.constraint import Constraint, _ConstraintData +from pyomo.core.base.constraint import Constraint, ConstraintData import logging @@ -55,7 +55,7 @@ def calculate_variable_from_constraint( ----------- variable: :py:class:`_VarData` The variable to solve for - constraint: :py:class:`_ConstraintData` or relational expression or `tuple` + constraint: :py:class:`ConstraintData` or relational expression or `tuple` The equality constraint to use to solve for the variable value. May be a `ConstraintData` object or any valid argument for ``Constraint(expr=<>)`` (i.e., a relational expression or 2- or @@ -81,7 +81,7 @@ def calculate_variable_from_constraint( """ # Leverage all the Constraint logic to process the incoming tuple/expression - if not isinstance(constraint, _ConstraintData): + if not isinstance(constraint, ConstraintData): constraint = Constraint(expr=constraint, name=type(constraint).__name__) constraint.construct() From 61c91d065eaf51cbcef2636a836566777239edc0 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:37:15 -0600 Subject: [PATCH 07/83] Renamed _DisjunctData -> DisjunctData --- pyomo/contrib/gdp_bounds/info.py | 4 ++-- pyomo/gdp/disjunct.py | 27 ++++++++++++++++----------- pyomo/gdp/plugins/hull.py | 2 +- pyomo/gdp/tests/test_bigm.py | 2 +- pyomo/gdp/util.py | 4 ++-- 5 files changed, 22 insertions(+), 17 deletions(-) diff --git a/pyomo/contrib/gdp_bounds/info.py b/pyomo/contrib/gdp_bounds/info.py index 6f39af5908d..db3f6d0846d 100644 --- a/pyomo/contrib/gdp_bounds/info.py +++ b/pyomo/contrib/gdp_bounds/info.py @@ -37,8 +37,8 @@ def disjunctive_bound(var, scope): Args: var (_VarData): Variable for which to compute bound scope (Component): The scope in which to compute the bound. If not a - _DisjunctData, it will walk up the tree and use the scope of the - most immediate enclosing _DisjunctData. + DisjunctData, it will walk up the tree and use the scope of the + most immediate enclosing DisjunctData. Returns: numeric: the tighter of either the disjunctive lower bound, the diff --git a/pyomo/gdp/disjunct.py b/pyomo/gdp/disjunct.py index de021d37547..dd9d2b4638c 100644 --- a/pyomo/gdp/disjunct.py +++ b/pyomo/gdp/disjunct.py @@ -412,7 +412,7 @@ def process(arg): return (_Initializer.deferred_value, arg) -class _DisjunctData(BlockData): +class DisjunctData(BlockData): __autoslot_mappers__ = {'_transformation_block': AutoSlots.weakref_mapper} _Block_reserved_words = set() @@ -434,23 +434,28 @@ def __init__(self, component): self._transformation_block = None def activate(self): - super(_DisjunctData, self).activate() + super(DisjunctData, self).activate() self.indicator_var.unfix() def deactivate(self): - super(_DisjunctData, self).deactivate() + super(DisjunctData, self).deactivate() self.indicator_var.fix(False) def _deactivate_without_fixing_indicator(self): - super(_DisjunctData, self).deactivate() + super(DisjunctData, self).deactivate() def _activate_without_unfixing_indicator(self): - super(_DisjunctData, self).activate() + super(DisjunctData, self).activate() + + +class _DisjunctData(metaclass=RenamedClass): + __renamed__new_class__ = DisjunctData + __renamed__version__ = '6.7.2.dev0' @ModelComponentFactory.register("Disjunctive blocks.") class Disjunct(Block): - _ComponentDataClass = _DisjunctData + _ComponentDataClass = DisjunctData def __new__(cls, *args, **kwds): if cls != Disjunct: @@ -475,7 +480,7 @@ def __init__(self, *args, **kwargs): # def _deactivate_without_fixing_indicator(self): # # Ideally, this would be a super call from this class. However, # # doing that would trigger a call to deactivate() on all the - # # _DisjunctData objects (exactly what we want to avoid!) + # # DisjunctData objects (exactly what we want to avoid!) # # # # For the time being, we will do something bad and directly call # # the base class method from where we would otherwise want to @@ -484,7 +489,7 @@ def __init__(self, *args, **kwargs): def _activate_without_unfixing_indicator(self): # Ideally, this would be a super call from this class. However, # doing that would trigger a call to deactivate() on all the - # _DisjunctData objects (exactly what we want to avoid!) + # DisjunctData objects (exactly what we want to avoid!) # # For the time being, we will do something bad and directly call # the base class method from where we would otherwise want to @@ -495,7 +500,7 @@ def _activate_without_unfixing_indicator(self): component_data._activate_without_unfixing_indicator() -class ScalarDisjunct(_DisjunctData, Disjunct): +class ScalarDisjunct(DisjunctData, Disjunct): def __init__(self, *args, **kwds): ## FIXME: This is a HACK to get around a chicken-and-egg issue ## where BlockData creates the indicator_var *before* @@ -503,7 +508,7 @@ def __init__(self, *args, **kwds): self._defer_construction = True self._suppress_ctypes = set() - _DisjunctData.__init__(self, self) + DisjunctData.__init__(self, self) Disjunct.__init__(self, *args, **kwds) self._data[None] = self self._index = UnindexedComponent_index @@ -524,7 +529,7 @@ def active(self): return any(d.active for d in self._data.values()) -_DisjunctData._Block_reserved_words = set(dir(Disjunct())) +DisjunctData._Block_reserved_words = set(dir(Disjunct())) class _DisjunctionData(ActiveComponentData): diff --git a/pyomo/gdp/plugins/hull.py b/pyomo/gdp/plugins/hull.py index 134a3d16d66..854366c0cf0 100644 --- a/pyomo/gdp/plugins/hull.py +++ b/pyomo/gdp/plugins/hull.py @@ -42,7 +42,7 @@ Binary, ) from pyomo.gdp import Disjunct, Disjunction, GDP_Error -from pyomo.gdp.disjunct import _DisjunctData +from pyomo.gdp.disjunct import DisjunctData from pyomo.gdp.plugins.gdp_to_mip_transformation import GDP_to_MIP_Transformation from pyomo.gdp.transformed_disjunct import _TransformedDisjunct from pyomo.gdp.util import ( diff --git a/pyomo/gdp/tests/test_bigm.py b/pyomo/gdp/tests/test_bigm.py index bf0239d15e0..d5dcef3ba58 100644 --- a/pyomo/gdp/tests/test_bigm.py +++ b/pyomo/gdp/tests/test_bigm.py @@ -2196,7 +2196,7 @@ def test_do_not_assume_nested_indicators_local(self): class IndexedDisjunction(unittest.TestCase): # this tests that if the targets are a subset of the - # _DisjunctDatas in an IndexedDisjunction that the xor constraint + # DisjunctDatas in an IndexedDisjunction that the xor constraint # created on the parent block will still be indexed as expected. def test_xor_constraint(self): ct.check_indexed_xor_constraints_with_targets(self, 'bigm') diff --git a/pyomo/gdp/util.py b/pyomo/gdp/util.py index 2164671ea16..686253b0179 100644 --- a/pyomo/gdp/util.py +++ b/pyomo/gdp/util.py @@ -10,7 +10,7 @@ # ___________________________________________________________________________ from pyomo.gdp import GDP_Error, Disjunction -from pyomo.gdp.disjunct import _DisjunctData, Disjunct +from pyomo.gdp.disjunct import DisjunctData, Disjunct import pyomo.core.expr as EXPR from pyomo.core.base.component import _ComponentBase @@ -493,7 +493,7 @@ def get_src_constraint(transformedConstraint): def _find_parent_disjunct(constraint): # traverse up until we find the disjunct this constraint lives on parent_disjunct = constraint.parent_block() - while not isinstance(parent_disjunct, _DisjunctData): + while not isinstance(parent_disjunct, DisjunctData): if parent_disjunct is None: raise GDP_Error( "Constraint '%s' is not on a disjunct and so was not " From 47a7e26da00a1520e5903e16baeb6ce076b155c6 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:37:32 -0600 Subject: [PATCH 08/83] Renamed _DisjunctionData -> DisjunctionData --- pyomo/core/base/component.py | 2 +- pyomo/gdp/disjunct.py | 15 ++++++++++----- 2 files changed, 11 insertions(+), 6 deletions(-) diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 7d6fc903632..dcaf976356b 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -805,7 +805,7 @@ class ComponentData(_ComponentBase): # classes: BooleanVarData, ConnectorData, ConstraintData, # _GeneralExpressionData, _LogicalConstraintData, # _GeneralLogicalConstraintData, _GeneralObjectiveData, - # _ParamData,_GeneralVarData, _GeneralBooleanVarData, _DisjunctionData, + # _ParamData,_GeneralVarData, _GeneralBooleanVarData, DisjunctionData, # ArcData, _PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those # constructors as well! diff --git a/pyomo/gdp/disjunct.py b/pyomo/gdp/disjunct.py index dd9d2b4638c..658ead27783 100644 --- a/pyomo/gdp/disjunct.py +++ b/pyomo/gdp/disjunct.py @@ -532,7 +532,7 @@ def active(self): DisjunctData._Block_reserved_words = set(dir(Disjunct())) -class _DisjunctionData(ActiveComponentData): +class DisjunctionData(ActiveComponentData): __slots__ = ('disjuncts', 'xor', '_algebraic_constraint', '_transformation_map') __autoslot_mappers__ = {'_algebraic_constraint': AutoSlots.weakref_mapper} _NoArgument = (0,) @@ -625,9 +625,14 @@ def set_value(self, expr): self.disjuncts.append(disjunct) +class _DisjunctionData(metaclass=RenamedClass): + __renamed__new_class__ = DisjunctionData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register("Disjunction expressions.") class Disjunction(ActiveIndexedComponent): - _ComponentDataClass = _DisjunctionData + _ComponentDataClass = DisjunctionData def __new__(cls, *args, **kwds): if cls != Disjunction: @@ -768,9 +773,9 @@ def _pprint(self): ) -class ScalarDisjunction(_DisjunctionData, Disjunction): +class ScalarDisjunction(DisjunctionData, Disjunction): def __init__(self, *args, **kwds): - _DisjunctionData.__init__(self, component=self) + DisjunctionData.__init__(self, component=self) Disjunction.__init__(self, *args, **kwds) self._index = UnindexedComponent_index @@ -781,7 +786,7 @@ def __init__(self, *args, **kwds): # currently in place). So during initialization only, we will # treat them as "indexed" objects where things like # Constraint.Skip are managed. But after that they will behave - # like _DisjunctionData objects where set_value does not handle + # like DisjunctionData objects where set_value does not handle # Disjunction.Skip but expects a valid expression or None. # From 4320bc1c068ea2b812f22e149378fe9fc7770291 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:38:42 -0600 Subject: [PATCH 09/83] Renamed _ExpressionData -> ExpressionData --- pyomo/contrib/mcpp/pyomo_mcpp.py | 4 ++-- pyomo/core/base/__init__.py | 2 +- pyomo/core/base/expression.py | 11 ++++++++--- pyomo/core/base/objective.py | 4 ++-- pyomo/core/beta/dict_objects.py | 4 ++-- pyomo/core/beta/list_objects.py | 4 ++-- pyomo/gdp/tests/test_util.py | 6 +++--- pyomo/repn/plugins/ampl/ampl_.py | 4 ++-- pyomo/repn/standard_repn.py | 6 +++--- pyomo/repn/util.py | 4 ++-- 10 files changed, 27 insertions(+), 22 deletions(-) diff --git a/pyomo/contrib/mcpp/pyomo_mcpp.py b/pyomo/contrib/mcpp/pyomo_mcpp.py index 35e883f98da..1375ae61c50 100644 --- a/pyomo/contrib/mcpp/pyomo_mcpp.py +++ b/pyomo/contrib/mcpp/pyomo_mcpp.py @@ -20,7 +20,7 @@ from pyomo.common.fileutils import Library from pyomo.core import value, Expression from pyomo.core.base.block import SubclassOf -from pyomo.core.base.expression import _ExpressionData +from pyomo.core.base.expression import ExpressionData from pyomo.core.expr.numvalue import nonpyomo_leaf_types from pyomo.core.expr.numeric_expr import ( AbsExpression, @@ -307,7 +307,7 @@ def exitNode(self, node, data): ans = self.mcpp.newConstant(node) elif not node.is_expression_type(): ans = self.register_num(node) - elif type(node) in SubclassOf(Expression) or isinstance(node, _ExpressionData): + elif type(node) in SubclassOf(Expression) or isinstance(node, ExpressionData): ans = data[0] else: raise RuntimeError("Unhandled expression type: %s" % (type(node))) diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 9a5337ac2c8..d875065d502 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -36,7 +36,7 @@ from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base.config import PyomoOptions -from pyomo.core.base.expression import Expression, _ExpressionData +from pyomo.core.base.expression import Expression, ExpressionData from pyomo.core.base.label import ( CuidLabeler, CounterLabeler, diff --git a/pyomo/core/base/expression.py b/pyomo/core/base/expression.py index 3ce998b62a4..e21613fcbb1 100644 --- a/pyomo/core/base/expression.py +++ b/pyomo/core/base/expression.py @@ -36,7 +36,7 @@ logger = logging.getLogger('pyomo.core') -class _ExpressionData(numeric_expr.NumericValue): +class ExpressionData(numeric_expr.NumericValue): """ An object that defines a named expression. @@ -137,13 +137,18 @@ def is_fixed(self): """A boolean indicating whether this expression is fixed.""" raise NotImplementedError - # _ExpressionData should never return False because + # ExpressionData should never return False because # they can store subexpressions that contain variables def is_potentially_variable(self): return True -class _GeneralExpressionDataImpl(_ExpressionData): +class _ExpressionData(metaclass=RenamedClass): + __renamed__new_class__ = ExpressionData + __renamed__version__ = '6.7.2.dev0' + + +class _GeneralExpressionDataImpl(ExpressionData): """ An object that defines an expression that is never cloned diff --git a/pyomo/core/base/objective.py b/pyomo/core/base/objective.py index fcc63755f2b..d259358dcd7 100644 --- a/pyomo/core/base/objective.py +++ b/pyomo/core/base/objective.py @@ -28,7 +28,7 @@ UnindexedComponent_set, rule_wrapper, ) -from pyomo.core.base.expression import _ExpressionData, _GeneralExpressionDataImpl +from pyomo.core.base.expression import ExpressionData, _GeneralExpressionDataImpl from pyomo.core.base.set import Set from pyomo.core.base.initializer import ( Initializer, @@ -86,7 +86,7 @@ def O_rule(model, i, j): # -class _ObjectiveData(_ExpressionData): +class _ObjectiveData(ExpressionData): """ This class defines the data for a single objective. diff --git a/pyomo/core/beta/dict_objects.py b/pyomo/core/beta/dict_objects.py index 53d39939db2..2b23d81e91a 100644 --- a/pyomo/core/beta/dict_objects.py +++ b/pyomo/core/beta/dict_objects.py @@ -17,7 +17,7 @@ from pyomo.core.base.var import IndexedVar, _VarData from pyomo.core.base.constraint import IndexedConstraint, ConstraintData from pyomo.core.base.objective import IndexedObjective, _ObjectiveData -from pyomo.core.base.expression import IndexedExpression, _ExpressionData +from pyomo.core.base.expression import IndexedExpression, ExpressionData from collections.abc import MutableMapping from collections.abc import Mapping @@ -211,4 +211,4 @@ def __init__(self, *args, **kwds): # Constructor for ComponentDict needs to # go last in order to handle any initialization # iterable as an argument - ComponentDict.__init__(self, _ExpressionData, *args, **kwds) + ComponentDict.__init__(self, ExpressionData, *args, **kwds) diff --git a/pyomo/core/beta/list_objects.py b/pyomo/core/beta/list_objects.py index e8b40e6da53..dd199eb70cd 100644 --- a/pyomo/core/beta/list_objects.py +++ b/pyomo/core/beta/list_objects.py @@ -17,7 +17,7 @@ from pyomo.core.base.var import IndexedVar, _VarData from pyomo.core.base.constraint import IndexedConstraint, ConstraintData from pyomo.core.base.objective import IndexedObjective, _ObjectiveData -from pyomo.core.base.expression import IndexedExpression, _ExpressionData +from pyomo.core.base.expression import IndexedExpression, ExpressionData from collections.abc import MutableSequence @@ -259,4 +259,4 @@ def __init__(self, *args, **kwds): # Constructor for ComponentList needs to # go last in order to handle any initialization # iterable as an argument - ComponentList.__init__(self, _ExpressionData, *args, **kwds) + ComponentList.__init__(self, ExpressionData, *args, **kwds) diff --git a/pyomo/gdp/tests/test_util.py b/pyomo/gdp/tests/test_util.py index fd555fc2f59..8ea72af37da 100644 --- a/pyomo/gdp/tests/test_util.py +++ b/pyomo/gdp/tests/test_util.py @@ -13,7 +13,7 @@ from pyomo.core import ConcreteModel, Var, Expression, Block, RangeSet, Any import pyomo.core.expr as EXPR -from pyomo.core.base.expression import _ExpressionData +from pyomo.core.base.expression import ExpressionData from pyomo.gdp.util import ( clone_without_expression_components, is_child_of, @@ -40,7 +40,7 @@ def test_clone_without_expression_components(self): test = clone_without_expression_components(base, {}) self.assertIsNot(base, test) self.assertEqual(base(), test()) - self.assertIsInstance(base, _ExpressionData) + self.assertIsInstance(base, ExpressionData) self.assertIsInstance(test, EXPR.SumExpression) test = clone_without_expression_components(base, {id(m.x): m.y}) self.assertEqual(3**2 + 3 - 1, test()) @@ -51,7 +51,7 @@ def test_clone_without_expression_components(self): self.assertEqual(base(), test()) self.assertIsInstance(base, EXPR.SumExpression) self.assertIsInstance(test, EXPR.SumExpression) - self.assertIsInstance(base.arg(0), _ExpressionData) + self.assertIsInstance(base.arg(0), ExpressionData) self.assertIsInstance(test.arg(0), EXPR.SumExpression) test = clone_without_expression_components(base, {id(m.x): m.y}) self.assertEqual(3**2 + 3 - 1 + 3, test()) diff --git a/pyomo/repn/plugins/ampl/ampl_.py b/pyomo/repn/plugins/ampl/ampl_.py index f422a085a3c..c6357cbecd9 100644 --- a/pyomo/repn/plugins/ampl/ampl_.py +++ b/pyomo/repn/plugins/ampl/ampl_.py @@ -33,7 +33,7 @@ from pyomo.core.base import ( SymbolMap, NameLabeler, - _ExpressionData, + ExpressionData, SortComponents, var, param, @@ -724,7 +724,7 @@ def _print_nonlinear_terms_NL(self, exp): self._print_nonlinear_terms_NL(exp.arg(0)) self._print_nonlinear_terms_NL(exp.arg(1)) - elif isinstance(exp, (_ExpressionData, IIdentityExpression)): + elif isinstance(exp, (ExpressionData, IIdentityExpression)): self._print_nonlinear_terms_NL(exp.expr) else: diff --git a/pyomo/repn/standard_repn.py b/pyomo/repn/standard_repn.py index 455e7bd9444..70368dd3d7e 100644 --- a/pyomo/repn/standard_repn.py +++ b/pyomo/repn/standard_repn.py @@ -20,7 +20,7 @@ import pyomo.core.expr as EXPR from pyomo.core.expr.numvalue import NumericConstant from pyomo.core.base.objective import _GeneralObjectiveData, ScalarObjective -from pyomo.core.base import _ExpressionData, Expression +from pyomo.core.base import ExpressionData, Expression from pyomo.core.base.expression import ScalarExpression, _GeneralExpressionData from pyomo.core.base.var import ScalarVar, Var, _GeneralVarData, value from pyomo.core.base.param import ScalarParam, _ParamData @@ -1152,7 +1152,7 @@ def _collect_external_fn(exp, multiplier, idMap, compute_values, verbose, quadra ScalarExpression: _collect_identity, expression: _collect_identity, noclone: _collect_identity, - _ExpressionData: _collect_identity, + ExpressionData: _collect_identity, Expression: _collect_identity, _GeneralObjectiveData: _collect_identity, ScalarObjective: _collect_identity, @@ -1551,7 +1551,7 @@ def _linear_collect_pow(exp, multiplier, idMap, compute_values, verbose, coef): ScalarExpression : _linear_collect_identity, expression : _linear_collect_identity, noclone : _linear_collect_identity, - _ExpressionData : _linear_collect_identity, + ExpressionData : _linear_collect_identity, Expression : _linear_collect_identity, _GeneralObjectiveData : _linear_collect_identity, ScalarObjective : _linear_collect_identity, diff --git a/pyomo/repn/util.py b/pyomo/repn/util.py index b4a21a2108f..7351ea51c58 100644 --- a/pyomo/repn/util.py +++ b/pyomo/repn/util.py @@ -40,7 +40,7 @@ SortComponents, ) from pyomo.core.base.component import ActiveComponent -from pyomo.core.base.expression import _ExpressionData +from pyomo.core.base.expression import ExpressionData from pyomo.core.expr.numvalue import is_fixed, value import pyomo.core.expr as EXPR import pyomo.core.kernel as kernel @@ -55,7 +55,7 @@ EXPR.NPV_SumExpression, } _named_subexpression_types = ( - _ExpressionData, + ExpressionData, kernel.expression.expression, kernel.objective.objective, ) From 86192304769e54cfcd3900e7878d71a767b5446a Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:40:16 -0600 Subject: [PATCH 10/83] Renamed _FiniteRangeSetData -> FiniteRangeSetData --- pyomo/core/base/set.py | 17 +++++++++++------ pyomo/core/tests/unit/test_set.py | 6 +++--- 2 files changed, 14 insertions(+), 9 deletions(-) diff --git a/pyomo/core/base/set.py b/pyomo/core/base/set.py index b3277ab3260..319f3b0e5ae 100644 --- a/pyomo/core/base/set.py +++ b/pyomo/core/base/set.py @@ -2648,7 +2648,7 @@ def ranges(self): return iter(self._ranges) -class _FiniteRangeSetData( +class FiniteRangeSetData( _SortedSetMixin, _OrderedSetMixin, _FiniteSetMixin, _InfiniteRangeSetData ): __slots__ = () @@ -2672,7 +2672,7 @@ def _iter_impl(self): # iterate over it nIters = len(self._ranges) - 1 if not nIters: - yield from _FiniteRangeSetData._range_gen(self._ranges[0]) + yield from FiniteRangeSetData._range_gen(self._ranges[0]) return # The trick here is that we need to remove any duplicates from @@ -2683,7 +2683,7 @@ def _iter_impl(self): for r in self._ranges: # Note: there should always be at least 1 member in each # NumericRange - i = _FiniteRangeSetData._range_gen(r) + i = FiniteRangeSetData._range_gen(r) iters.append([next(i), i]) iters.sort(reverse=True, key=lambda x: x[0]) @@ -2756,6 +2756,11 @@ def ord(self, item): domain = _InfiniteRangeSetData.domain +class _FiniteRangeSetData(metaclass=RenamedClass): + __renamed__new_class__ = FiniteRangeSetData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register( "A sequence of numeric values. RangeSet(start,end,step) is a sequence " "starting a value 'start', and increasing in values by 'step' until a " @@ -3120,7 +3125,7 @@ def construct(self, data=None): old_ranges.reverse() while old_ranges: r = old_ranges.pop() - for i, val in enumerate(_FiniteRangeSetData._range_gen(r)): + for i, val in enumerate(FiniteRangeSetData._range_gen(r)): if not _filter(_block, val): split_r = r.range_difference((NumericRange(val, val, 0),)) if len(split_r) == 2: @@ -3233,9 +3238,9 @@ class InfiniteSimpleRangeSet(metaclass=RenamedClass): __renamed__version__ = '6.0' -class FiniteScalarRangeSet(_ScalarOrderedSetMixin, _FiniteRangeSetData, RangeSet): +class FiniteScalarRangeSet(_ScalarOrderedSetMixin, FiniteRangeSetData, RangeSet): def __init__(self, *args, **kwds): - _FiniteRangeSetData.__init__(self, component=self) + FiniteRangeSetData.__init__(self, component=self) RangeSet.__init__(self, *args, **kwds) self._index = UnindexedComponent_index diff --git a/pyomo/core/tests/unit/test_set.py b/pyomo/core/tests/unit/test_set.py index 4bbac6ecaa0..3639aa82c73 100644 --- a/pyomo/core/tests/unit/test_set.py +++ b/pyomo/core/tests/unit/test_set.py @@ -60,7 +60,7 @@ FiniteSetOf, InfiniteSetOf, RangeSet, - _FiniteRangeSetData, + FiniteRangeSetData, _InfiniteRangeSetData, FiniteScalarRangeSet, InfiniteScalarRangeSet, @@ -1285,13 +1285,13 @@ def test_is_functions(self): self.assertTrue(i.isdiscrete()) self.assertTrue(i.isfinite()) self.assertTrue(i.isordered()) - self.assertIsInstance(i, _FiniteRangeSetData) + self.assertIsInstance(i, FiniteRangeSetData) i = RangeSet(1, 3) self.assertTrue(i.isdiscrete()) self.assertTrue(i.isfinite()) self.assertTrue(i.isordered()) - self.assertIsInstance(i, _FiniteRangeSetData) + self.assertIsInstance(i, FiniteRangeSetData) i = RangeSet(1, 3, 0) self.assertFalse(i.isdiscrete()) From 4ea182da5dab8f6994cbf7bc17a0cd1fc1b2f1ec Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:40:42 -0600 Subject: [PATCH 11/83] Renamed _FiniteSetData -> FiniteSetData --- pyomo/core/base/set.py | 17 +++++++++++------ pyomo/core/tests/unit/test_set.py | 8 ++++---- 2 files changed, 15 insertions(+), 10 deletions(-) diff --git a/pyomo/core/base/set.py b/pyomo/core/base/set.py index 319f3b0e5ae..8db64620d5c 100644 --- a/pyomo/core/base/set.py +++ b/pyomo/core/base/set.py @@ -1294,7 +1294,7 @@ def ranges(self): yield NonNumericRange(i) -class _FiniteSetData(_FiniteSetMixin, _SetData): +class FiniteSetData(_FiniteSetMixin, _SetData): """A general unordered iterable Set""" __slots__ = ('_values', '_domain', '_validate', '_filter', '_dimen') @@ -1470,6 +1470,11 @@ def pop(self): return self._values.pop() +class _FiniteSetData(metaclass=RenamedClass): + __renamed__new_class__ = FiniteSetData + __renamed__version__ = '6.7.2.dev0' + + class _ScalarOrderedSetMixin(object): # This mixin is required because scalar ordered sets implement # __getitem__() as an alias of at() @@ -1630,7 +1635,7 @@ def _to_0_based_index(self, item): ) -class _OrderedSetData(_OrderedSetMixin, _FiniteSetData): +class _OrderedSetData(_OrderedSetMixin, FiniteSetData): """ This class defines the base class for an ordered set of concrete data. @@ -1652,7 +1657,7 @@ class _OrderedSetData(_OrderedSetMixin, _FiniteSetData): def __init__(self, component): self._values = {} self._ordered_values = [] - _FiniteSetData.__init__(self, component=component) + FiniteSetData.__init__(self, component=component) def _iter_impl(self): """ @@ -2034,7 +2039,7 @@ def __new__(cls, *args, **kwds): elif ordered is Set.SortedOrder: newObj._ComponentDataClass = _SortedSetData else: - newObj._ComponentDataClass = _FiniteSetData + newObj._ComponentDataClass = FiniteSetData return newObj @overload @@ -2388,9 +2393,9 @@ def __getitem__(self, index) -> _SetData: ... __getitem__ = IndexedComponent.__getitem__ # type: ignore -class FiniteScalarSet(_FiniteSetData, Set): +class FiniteScalarSet(FiniteSetData, Set): def __init__(self, **kwds): - _FiniteSetData.__init__(self, component=self) + FiniteSetData.__init__(self, component=self) Set.__init__(self, **kwds) self._index = UnindexedComponent_index diff --git a/pyomo/core/tests/unit/test_set.py b/pyomo/core/tests/unit/test_set.py index 3639aa82c73..a9b9fb9469b 100644 --- a/pyomo/core/tests/unit/test_set.py +++ b/pyomo/core/tests/unit/test_set.py @@ -82,7 +82,7 @@ SetProduct_FiniteSet, SetProduct_OrderedSet, _SetData, - _FiniteSetData, + FiniteSetData, _InsertionOrderSetData, _SortedSetData, _FiniteSetMixin, @@ -4137,9 +4137,9 @@ def test_indexed_set(self): self.assertFalse(m.I[1].isordered()) self.assertFalse(m.I[2].isordered()) self.assertFalse(m.I[3].isordered()) - self.assertIs(type(m.I[1]), _FiniteSetData) - self.assertIs(type(m.I[2]), _FiniteSetData) - self.assertIs(type(m.I[3]), _FiniteSetData) + self.assertIs(type(m.I[1]), FiniteSetData) + self.assertIs(type(m.I[2]), FiniteSetData) + self.assertIs(type(m.I[3]), FiniteSetData) self.assertEqual(m.I.data(), {1: (1,), 2: (2,), 3: (4,)}) # Explicit (constant) construction From 3a86baa8bcb6152edca7c4e687488e6c5de08137 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:41:02 -0600 Subject: [PATCH 12/83] Renamed _GeneralBooleanVarData -> GeneralBooleanVarData --- pyomo/contrib/cp/repn/docplex_writer.py | 4 +-- .../logical_to_disjunctive_walker.py | 2 +- pyomo/core/base/__init__.py | 2 +- pyomo/core/base/boolean_var.py | 27 +++++++++++-------- pyomo/core/base/component.py | 2 +- 5 files changed, 21 insertions(+), 16 deletions(-) diff --git a/pyomo/contrib/cp/repn/docplex_writer.py b/pyomo/contrib/cp/repn/docplex_writer.py index 8356a1e752f..510bbf4e398 100644 --- a/pyomo/contrib/cp/repn/docplex_writer.py +++ b/pyomo/contrib/cp/repn/docplex_writer.py @@ -60,7 +60,7 @@ ) from pyomo.core.base.boolean_var import ( ScalarBooleanVar, - _GeneralBooleanVarData, + GeneralBooleanVarData, IndexedBooleanVar, ) from pyomo.core.base.expression import ScalarExpression, _GeneralExpressionData @@ -964,7 +964,7 @@ class LogicalToDoCplex(StreamBasedExpressionVisitor): _GeneralVarData: _before_var, IndexedVar: _before_indexed_var, ScalarBooleanVar: _before_boolean_var, - _GeneralBooleanVarData: _before_boolean_var, + GeneralBooleanVarData: _before_boolean_var, IndexedBooleanVar: _before_indexed_boolean_var, _GeneralExpressionData: _before_named_expression, ScalarExpression: _before_named_expression, diff --git a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py index d5f13e91535..548078f55f8 100644 --- a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py +++ b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py @@ -209,7 +209,7 @@ def _dispatch_atmost(visitor, node, *args): _before_child_dispatcher = {} _before_child_dispatcher[BV.ScalarBooleanVar] = _dispatch_boolean_var -_before_child_dispatcher[BV._GeneralBooleanVarData] = _dispatch_boolean_var +_before_child_dispatcher[BV.GeneralBooleanVarData] = _dispatch_boolean_var _before_child_dispatcher[AutoLinkedBooleanVar] = _dispatch_boolean_var _before_child_dispatcher[_ParamData] = _dispatch_param _before_child_dispatcher[ScalarParam] = _dispatch_param diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index d875065d502..bb62cb96782 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -61,7 +61,7 @@ from pyomo.core.base.boolean_var import ( BooleanVar, BooleanVarData, - _GeneralBooleanVarData, + GeneralBooleanVarData, BooleanVarList, ScalarBooleanVar, ) diff --git a/pyomo/core/base/boolean_var.py b/pyomo/core/base/boolean_var.py index bf9d6159754..287851a7f7e 100644 --- a/pyomo/core/base/boolean_var.py +++ b/pyomo/core/base/boolean_var.py @@ -194,7 +194,7 @@ def _associated_binary_mapper(encode, val): return val -class _GeneralBooleanVarData(BooleanVarData): +class GeneralBooleanVarData(BooleanVarData): """ This class defines the data for a single Boolean variable. @@ -271,13 +271,13 @@ def stale(self, val): def get_associated_binary(self): """Get the binary _VarData associated with this - _GeneralBooleanVarData""" + GeneralBooleanVarData""" return ( self._associated_binary() if self._associated_binary is not None else None ) def associate_binary_var(self, binary_var): - """Associate a binary _VarData to this _GeneralBooleanVarData""" + """Associate a binary _VarData to this GeneralBooleanVarData""" if ( self._associated_binary is not None and type(self._associated_binary) @@ -300,6 +300,11 @@ def associate_binary_var(self, binary_var): self._associated_binary = weakref_ref(binary_var) +class _GeneralBooleanVarData(metaclass=RenamedClass): + __renamed__new_class__ = GeneralBooleanVarData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register("Logical decision variables.") class BooleanVar(IndexedComponent): """A logical variable, which may be defined over an index. @@ -314,7 +319,7 @@ class BooleanVar(IndexedComponent): to True. """ - _ComponentDataClass = _GeneralBooleanVarData + _ComponentDataClass = GeneralBooleanVarData def __new__(cls, *args, **kwds): if cls != BooleanVar: @@ -506,11 +511,11 @@ def _pprint(self): ) -class ScalarBooleanVar(_GeneralBooleanVarData, BooleanVar): +class ScalarBooleanVar(GeneralBooleanVarData, BooleanVar): """A single variable.""" def __init__(self, *args, **kwd): - _GeneralBooleanVarData.__init__(self, component=self) + GeneralBooleanVarData.__init__(self, component=self) BooleanVar.__init__(self, *args, **kwd) self._index = UnindexedComponent_index @@ -526,7 +531,7 @@ def __init__(self, *args, **kwd): def value(self): """Return the value for this variable.""" if self._constructed: - return _GeneralBooleanVarData.value.fget(self) + return GeneralBooleanVarData.value.fget(self) raise ValueError( "Accessing the value of variable '%s' " "before the Var has been constructed (there " @@ -537,7 +542,7 @@ def value(self): def value(self, val): """Set the value for this variable.""" if self._constructed: - return _GeneralBooleanVarData.value.fset(self, val) + return GeneralBooleanVarData.value.fset(self, val) raise ValueError( "Setting the value of variable '%s' " "before the Var has been constructed (there " @@ -546,7 +551,7 @@ def value(self, val): @property def domain(self): - return _GeneralBooleanVarData.domain.fget(self) + return GeneralBooleanVarData.domain.fget(self) def fix(self, value=NOTSET, skip_validation=False): """ @@ -554,7 +559,7 @@ def fix(self, value=NOTSET, skip_validation=False): indicating the variable should be fixed at its current value. """ if self._constructed: - return _GeneralBooleanVarData.fix(self, value, skip_validation) + return GeneralBooleanVarData.fix(self, value, skip_validation) raise ValueError( "Fixing variable '%s' " "before the Var has been constructed (there " @@ -564,7 +569,7 @@ def fix(self, value=NOTSET, skip_validation=False): def unfix(self): """Sets the fixed indicator to False.""" if self._constructed: - return _GeneralBooleanVarData.unfix(self) + return GeneralBooleanVarData.unfix(self) raise ValueError( "Freeing variable '%s' " "before the Var has been constructed (there " diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index dcaf976356b..1317c928686 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -805,7 +805,7 @@ class ComponentData(_ComponentBase): # classes: BooleanVarData, ConnectorData, ConstraintData, # _GeneralExpressionData, _LogicalConstraintData, # _GeneralLogicalConstraintData, _GeneralObjectiveData, - # _ParamData,_GeneralVarData, _GeneralBooleanVarData, DisjunctionData, + # _ParamData,_GeneralVarData, GeneralBooleanVarData, DisjunctionData, # ArcData, _PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those # constructors as well! From 80c064ac99ac5870cc1439f4cd3405f7565a3516 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:42:40 -0600 Subject: [PATCH 13/83] Renamed _GeneralConstraintData -> GeneralConstraintData --- pyomo/contrib/appsi/base.py | 48 +++++++++---------- pyomo/contrib/appsi/fbbt.py | 6 +-- pyomo/contrib/appsi/solvers/cbc.py | 6 +-- pyomo/contrib/appsi/solvers/cplex.py | 10 ++-- pyomo/contrib/appsi/solvers/gurobi.py | 16 +++---- pyomo/contrib/appsi/solvers/highs.py | 6 +-- pyomo/contrib/appsi/solvers/ipopt.py | 10 ++-- pyomo/contrib/appsi/solvers/wntr.py | 6 +-- pyomo/contrib/appsi/writers/lp_writer.py | 6 +-- pyomo/contrib/appsi/writers/nl_writer.py | 6 +-- pyomo/contrib/solver/base.py | 10 ++-- pyomo/contrib/solver/gurobi.py | 16 +++---- pyomo/contrib/solver/persistent.py | 12 ++--- pyomo/contrib/solver/solution.py | 14 +++--- .../contrib/solver/tests/unit/test_results.py | 6 +-- pyomo/core/base/constraint.py | 27 ++++++----- pyomo/core/tests/unit/test_con.py | 4 +- pyomo/core/tests/unit/test_dict_objects.py | 4 +- pyomo/core/tests/unit/test_list_objects.py | 4 +- pyomo/gdp/tests/common_tests.py | 4 +- pyomo/gdp/tests/test_bigm.py | 4 +- pyomo/gdp/tests/test_hull.py | 4 +- .../plugins/solvers/gurobi_persistent.py | 10 ++-- 23 files changed, 121 insertions(+), 118 deletions(-) diff --git a/pyomo/contrib/appsi/base.py b/pyomo/contrib/appsi/base.py index b4ade16a597..d5982fc72e6 100644 --- a/pyomo/contrib/appsi/base.py +++ b/pyomo/contrib/appsi/base.py @@ -21,7 +21,7 @@ Tuple, MutableMapping, ) -from pyomo.core.base.constraint import _GeneralConstraintData, Constraint +from pyomo.core.base.constraint import GeneralConstraintData, Constraint from pyomo.core.base.sos import _SOSConstraintData, SOSConstraint from pyomo.core.base.var import _GeneralVarData, Var from pyomo.core.base.param import _ParamData, Param @@ -216,8 +216,8 @@ def get_primals( pass def get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: """ Returns a dictionary mapping constraint to dual value. @@ -235,8 +235,8 @@ def get_duals( raise NotImplementedError(f'{type(self)} does not support the get_duals method') def get_slacks( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: """ Returns a dictionary mapping constraint to slack. @@ -319,8 +319,8 @@ def get_primals( return primals def get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: if self._duals is None: raise RuntimeError( 'Solution loader does not currently have valid duals. Please ' @@ -336,8 +336,8 @@ def get_duals( return duals def get_slacks( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: if self._slacks is None: raise RuntimeError( 'Solution loader does not currently have valid slacks. Please ' @@ -731,8 +731,8 @@ def get_primals( pass def get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: """ Declare sign convention in docstring here. @@ -752,8 +752,8 @@ def get_duals( ) def get_slacks( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: """ Parameters ---------- @@ -807,7 +807,7 @@ def add_params(self, params: List[_ParamData]): pass @abc.abstractmethod - def add_constraints(self, cons: List[_GeneralConstraintData]): + def add_constraints(self, cons: List[GeneralConstraintData]): pass @abc.abstractmethod @@ -823,7 +823,7 @@ def remove_params(self, params: List[_ParamData]): pass @abc.abstractmethod - def remove_constraints(self, cons: List[_GeneralConstraintData]): + def remove_constraints(self, cons: List[GeneralConstraintData]): pass @abc.abstractmethod @@ -857,14 +857,14 @@ def get_primals(self, vars_to_load=None): return self._solver.get_primals(vars_to_load=vars_to_load) def get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: self._assert_solution_still_valid() return self._solver.get_duals(cons_to_load=cons_to_load) def get_slacks( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: self._assert_solution_still_valid() return self._solver.get_slacks(cons_to_load=cons_to_load) @@ -984,7 +984,7 @@ def add_params(self, params: List[_ParamData]): self._add_params(params) @abc.abstractmethod - def _add_constraints(self, cons: List[_GeneralConstraintData]): + def _add_constraints(self, cons: List[GeneralConstraintData]): pass def _check_for_new_vars(self, variables: List[_GeneralVarData]): @@ -1004,7 +1004,7 @@ def _check_to_remove_vars(self, variables: List[_GeneralVarData]): vars_to_remove[v_id] = v self.remove_variables(list(vars_to_remove.values())) - def add_constraints(self, cons: List[_GeneralConstraintData]): + def add_constraints(self, cons: List[GeneralConstraintData]): all_fixed_vars = dict() for con in cons: if con in self._named_expressions: @@ -1132,10 +1132,10 @@ def add_block(self, block): self.set_objective(obj) @abc.abstractmethod - def _remove_constraints(self, cons: List[_GeneralConstraintData]): + def _remove_constraints(self, cons: List[GeneralConstraintData]): pass - def remove_constraints(self, cons: List[_GeneralConstraintData]): + def remove_constraints(self, cons: List[GeneralConstraintData]): self._remove_constraints(cons) for con in cons: if con not in self._named_expressions: @@ -1334,7 +1334,7 @@ def update(self, timer: HierarchicalTimer = None): for c in self._vars_referenced_by_con.keys(): if c not in current_cons_dict and c not in current_sos_dict: if (c.ctype is Constraint) or ( - c.ctype is None and isinstance(c, _GeneralConstraintData) + c.ctype is None and isinstance(c, GeneralConstraintData) ): old_cons.append(c) else: diff --git a/pyomo/contrib/appsi/fbbt.py b/pyomo/contrib/appsi/fbbt.py index c6bbdb5bf3b..121557414b3 100644 --- a/pyomo/contrib/appsi/fbbt.py +++ b/pyomo/contrib/appsi/fbbt.py @@ -20,7 +20,7 @@ from typing import List, Optional from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.param import _ParamData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.objective import _GeneralObjectiveData, minimize, maximize from pyomo.core.base.block import BlockData @@ -154,7 +154,7 @@ def _add_params(self, params: List[_ParamData]): cp = cparams[ndx] cp.name = self._symbol_map.getSymbol(p, self._param_labeler) - def _add_constraints(self, cons: List[_GeneralConstraintData]): + def _add_constraints(self, cons: List[GeneralConstraintData]): cmodel.process_fbbt_constraints( self._cmodel, self._pyomo_expr_types, @@ -175,7 +175,7 @@ def _add_sos_constraints(self, cons: List[_SOSConstraintData]): 'IntervalTightener does not support SOS constraints' ) - def _remove_constraints(self, cons: List[_GeneralConstraintData]): + def _remove_constraints(self, cons: List[GeneralConstraintData]): if self._symbolic_solver_labels: for c in cons: self._symbol_map.removeSymbol(c) diff --git a/pyomo/contrib/appsi/solvers/cbc.py b/pyomo/contrib/appsi/solvers/cbc.py index 57bbf1b4c21..cc7327df11c 100644 --- a/pyomo/contrib/appsi/solvers/cbc.py +++ b/pyomo/contrib/appsi/solvers/cbc.py @@ -27,7 +27,7 @@ from pyomo.common.collections import ComponentMap from typing import Optional, Sequence, NoReturn, List, Mapping from pyomo.core.base.var import _GeneralVarData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData from pyomo.core.base.objective import _GeneralObjectiveData @@ -170,7 +170,7 @@ def add_variables(self, variables: List[_GeneralVarData]): def add_params(self, params: List[_ParamData]): self._writer.add_params(params) - def add_constraints(self, cons: List[_GeneralConstraintData]): + def add_constraints(self, cons: List[GeneralConstraintData]): self._writer.add_constraints(cons) def add_block(self, block: BlockData): @@ -182,7 +182,7 @@ def remove_variables(self, variables: List[_GeneralVarData]): def remove_params(self, params: List[_ParamData]): self._writer.remove_params(params) - def remove_constraints(self, cons: List[_GeneralConstraintData]): + def remove_constraints(self, cons: List[GeneralConstraintData]): self._writer.remove_constraints(cons) def remove_block(self, block: BlockData): diff --git a/pyomo/contrib/appsi/solvers/cplex.py b/pyomo/contrib/appsi/solvers/cplex.py index 2e04a979fda..222c466fb99 100644 --- a/pyomo/contrib/appsi/solvers/cplex.py +++ b/pyomo/contrib/appsi/solvers/cplex.py @@ -23,7 +23,7 @@ from pyomo.common.collections import ComponentMap from typing import Optional, Sequence, NoReturn, List, Mapping, Dict from pyomo.core.base.var import _GeneralVarData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData from pyomo.core.base.objective import _GeneralObjectiveData @@ -185,7 +185,7 @@ def add_variables(self, variables: List[_GeneralVarData]): def add_params(self, params: List[_ParamData]): self._writer.add_params(params) - def add_constraints(self, cons: List[_GeneralConstraintData]): + def add_constraints(self, cons: List[GeneralConstraintData]): self._writer.add_constraints(cons) def add_block(self, block: BlockData): @@ -197,7 +197,7 @@ def remove_variables(self, variables: List[_GeneralVarData]): def remove_params(self, params: List[_ParamData]): self._writer.remove_params(params) - def remove_constraints(self, cons: List[_GeneralConstraintData]): + def remove_constraints(self, cons: List[GeneralConstraintData]): self._writer.remove_constraints(cons) def remove_block(self, block: BlockData): @@ -389,8 +389,8 @@ def get_primals( return res def get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: if ( self._cplex_model.solution.get_solution_type() == self._cplex_model.solution.type.none diff --git a/pyomo/contrib/appsi/solvers/gurobi.py b/pyomo/contrib/appsi/solvers/gurobi.py index 1e18862e3bd..e20168034c6 100644 --- a/pyomo/contrib/appsi/solvers/gurobi.py +++ b/pyomo/contrib/appsi/solvers/gurobi.py @@ -24,7 +24,7 @@ from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler from pyomo.core.base.var import Var, _GeneralVarData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.param import _ParamData from pyomo.core.expr.numvalue import value, is_constant, is_fixed, native_numeric_types @@ -579,7 +579,7 @@ def _get_expr_from_pyomo_expr(self, expr): mutable_quadratic_coefficients, ) - def _add_constraints(self, cons: List[_GeneralConstraintData]): + def _add_constraints(self, cons: List[GeneralConstraintData]): for con in cons: conname = self._symbol_map.getSymbol(con, self._labeler) ( @@ -735,7 +735,7 @@ def _add_sos_constraints(self, cons: List[_SOSConstraintData]): self._constraints_added_since_update.update(cons) self._needs_updated = True - def _remove_constraints(self, cons: List[_GeneralConstraintData]): + def _remove_constraints(self, cons: List[GeneralConstraintData]): for con in cons: if con in self._constraints_added_since_update: self._update_gurobi_model() @@ -1195,7 +1195,7 @@ def set_linear_constraint_attr(self, con, attr, val): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be modified. attr: str @@ -1272,7 +1272,7 @@ def get_linear_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -1304,7 +1304,7 @@ def get_quadratic_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -1425,7 +1425,7 @@ def cbCut(self, con): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The cut to add """ if not con.active: @@ -1510,7 +1510,7 @@ def cbLazy(self, con): """ Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The lazy constraint to add """ if not con.active: diff --git a/pyomo/contrib/appsi/solvers/highs.py b/pyomo/contrib/appsi/solvers/highs.py index 3612b9d5014..7773d0624b2 100644 --- a/pyomo/contrib/appsi/solvers/highs.py +++ b/pyomo/contrib/appsi/solvers/highs.py @@ -21,7 +21,7 @@ from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap from pyomo.core.base.var import _GeneralVarData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.param import _ParamData from pyomo.core.expr.numvalue import value, is_constant @@ -376,7 +376,7 @@ def set_instance(self, model): if self._objective is None: self.set_objective(None) - def _add_constraints(self, cons: List[_GeneralConstraintData]): + def _add_constraints(self, cons: List[GeneralConstraintData]): self._sol = None if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() @@ -462,7 +462,7 @@ def _add_sos_constraints(self, cons: List[_SOSConstraintData]): 'Highs interface does not support SOS constraints' ) - def _remove_constraints(self, cons: List[_GeneralConstraintData]): + def _remove_constraints(self, cons: List[GeneralConstraintData]): self._sol = None if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() diff --git a/pyomo/contrib/appsi/solvers/ipopt.py b/pyomo/contrib/appsi/solvers/ipopt.py index 19ec5f8031c..75ebb10f719 100644 --- a/pyomo/contrib/appsi/solvers/ipopt.py +++ b/pyomo/contrib/appsi/solvers/ipopt.py @@ -29,7 +29,7 @@ from pyomo.core.expr.visitor import replace_expressions from typing import Optional, Sequence, NoReturn, List, Mapping from pyomo.core.base.var import _GeneralVarData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData from pyomo.core.base.objective import _GeneralObjectiveData @@ -234,7 +234,7 @@ def add_variables(self, variables: List[_GeneralVarData]): def add_params(self, params: List[_ParamData]): self._writer.add_params(params) - def add_constraints(self, cons: List[_GeneralConstraintData]): + def add_constraints(self, cons: List[GeneralConstraintData]): self._writer.add_constraints(cons) def add_block(self, block: BlockData): @@ -246,7 +246,7 @@ def remove_variables(self, variables: List[_GeneralVarData]): def remove_params(self, params: List[_ParamData]): self._writer.remove_params(params) - def remove_constraints(self, cons: List[_GeneralConstraintData]): + def remove_constraints(self, cons: List[GeneralConstraintData]): self._writer.remove_constraints(cons) def remove_block(self, block: BlockData): @@ -534,9 +534,7 @@ def get_primals( res[v] = self._primal_sol[v] return res - def get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ): + def get_duals(self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None): if ( self._last_results_object is None or self._last_results_object.termination_condition diff --git a/pyomo/contrib/appsi/solvers/wntr.py b/pyomo/contrib/appsi/solvers/wntr.py index 928eda2b514..c11536e2e6f 100644 --- a/pyomo/contrib/appsi/solvers/wntr.py +++ b/pyomo/contrib/appsi/solvers/wntr.py @@ -42,7 +42,7 @@ from pyomo.core.base.block import BlockData from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.param import _ParamData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.common.timing import HierarchicalTimer from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler from pyomo.common.dependencies import attempt_import @@ -278,7 +278,7 @@ def _add_params(self, params: List[_ParamData]): setattr(self._solver_model, pname, wntr_p) self._pyomo_param_to_solver_param_map[id(p)] = wntr_p - def _add_constraints(self, cons: List[_GeneralConstraintData]): + def _add_constraints(self, cons: List[GeneralConstraintData]): aml = wntr.sim.aml.aml for con in cons: if not con.equality: @@ -294,7 +294,7 @@ def _add_constraints(self, cons: List[_GeneralConstraintData]): self._pyomo_con_to_solver_con_map[con] = wntr_con self._needs_updated = True - def _remove_constraints(self, cons: List[_GeneralConstraintData]): + def _remove_constraints(self, cons: List[GeneralConstraintData]): for con in cons: solver_con = self._pyomo_con_to_solver_con_map[con] delattr(self._solver_model, solver_con.name) diff --git a/pyomo/contrib/appsi/writers/lp_writer.py b/pyomo/contrib/appsi/writers/lp_writer.py index 518be5fac99..39298bd1a61 100644 --- a/pyomo/contrib/appsi/writers/lp_writer.py +++ b/pyomo/contrib/appsi/writers/lp_writer.py @@ -12,7 +12,7 @@ from typing import List from pyomo.core.base.param import _ParamData from pyomo.core.base.var import _GeneralVarData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.block import BlockData @@ -99,14 +99,14 @@ def _add_params(self, params: List[_ParamData]): cp.value = p.value self._pyomo_param_to_solver_param_map[id(p)] = cp - def _add_constraints(self, cons: List[_GeneralConstraintData]): + def _add_constraints(self, cons: List[GeneralConstraintData]): cmodel.process_lp_constraints(cons, self) def _add_sos_constraints(self, cons: List[_SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('LP writer does not yet support SOS constraints') - def _remove_constraints(self, cons: List[_GeneralConstraintData]): + def _remove_constraints(self, cons: List[GeneralConstraintData]): for c in cons: cc = self._pyomo_con_to_solver_con_map.pop(c) self._writer.remove_constraint(cc) diff --git a/pyomo/contrib/appsi/writers/nl_writer.py b/pyomo/contrib/appsi/writers/nl_writer.py index 75b026ab521..3e13ef4077a 100644 --- a/pyomo/contrib/appsi/writers/nl_writer.py +++ b/pyomo/contrib/appsi/writers/nl_writer.py @@ -12,7 +12,7 @@ from typing import List from pyomo.core.base.param import _ParamData from pyomo.core.base.var import _GeneralVarData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.block import BlockData @@ -111,7 +111,7 @@ def _add_params(self, params: List[_ParamData]): cp = cparams[ndx] cp.name = self._symbol_map.getSymbol(p, self._param_labeler) - def _add_constraints(self, cons: List[_GeneralConstraintData]): + def _add_constraints(self, cons: List[GeneralConstraintData]): cmodel.process_nl_constraints( self._writer, self._expr_types, @@ -130,7 +130,7 @@ def _add_sos_constraints(self, cons: List[_SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('NL writer does not support SOS constraints') - def _remove_constraints(self, cons: List[_GeneralConstraintData]): + def _remove_constraints(self, cons: List[GeneralConstraintData]): if self.config.symbolic_solver_labels: for c in cons: self._symbol_map.removeSymbol(c) diff --git a/pyomo/contrib/solver/base.py b/pyomo/contrib/solver/base.py index 4b7da383a57..4b7d8f35ddc 100644 --- a/pyomo/contrib/solver/base.py +++ b/pyomo/contrib/solver/base.py @@ -14,7 +14,7 @@ from typing import Sequence, Dict, Optional, Mapping, NoReturn, List, Tuple import os -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.param import _ParamData from pyomo.core.base.block import BlockData @@ -232,8 +232,8 @@ def _get_primals( ) def _get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: """ Declare sign convention in docstring here. @@ -294,7 +294,7 @@ def add_parameters(self, params: List[_ParamData]): """ @abc.abstractmethod - def add_constraints(self, cons: List[_GeneralConstraintData]): + def add_constraints(self, cons: List[GeneralConstraintData]): """ Add constraints to the model """ @@ -318,7 +318,7 @@ def remove_parameters(self, params: List[_ParamData]): """ @abc.abstractmethod - def remove_constraints(self, cons: List[_GeneralConstraintData]): + def remove_constraints(self, cons: List[GeneralConstraintData]): """ Remove constraints from the model """ diff --git a/pyomo/contrib/solver/gurobi.py b/pyomo/contrib/solver/gurobi.py index d0ac0d80f45..cc95c0c5f0d 100644 --- a/pyomo/contrib/solver/gurobi.py +++ b/pyomo/contrib/solver/gurobi.py @@ -23,7 +23,7 @@ from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler from pyomo.core.base.var import _GeneralVarData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.param import _ParamData from pyomo.core.expr.numvalue import value, is_constant, is_fixed, native_numeric_types @@ -555,7 +555,7 @@ def _get_expr_from_pyomo_expr(self, expr): mutable_quadratic_coefficients, ) - def _add_constraints(self, cons: List[_GeneralConstraintData]): + def _add_constraints(self, cons: List[GeneralConstraintData]): for con in cons: conname = self._symbol_map.getSymbol(con, self._labeler) ( @@ -711,7 +711,7 @@ def _add_sos_constraints(self, cons: List[_SOSConstraintData]): self._constraints_added_since_update.update(cons) self._needs_updated = True - def _remove_constraints(self, cons: List[_GeneralConstraintData]): + def _remove_constraints(self, cons: List[GeneralConstraintData]): for con in cons: if con in self._constraints_added_since_update: self._update_gurobi_model() @@ -1125,7 +1125,7 @@ def set_linear_constraint_attr(self, con, attr, val): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be modified. attr: str @@ -1202,7 +1202,7 @@ def get_linear_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -1234,7 +1234,7 @@ def get_quadratic_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -1355,7 +1355,7 @@ def cbCut(self, con): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The cut to add """ if not con.active: @@ -1440,7 +1440,7 @@ def cbLazy(self, con): """ Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The lazy constraint to add """ if not con.active: diff --git a/pyomo/contrib/solver/persistent.py b/pyomo/contrib/solver/persistent.py index 4b1a7c58dcd..9b63e05ce46 100644 --- a/pyomo/contrib/solver/persistent.py +++ b/pyomo/contrib/solver/persistent.py @@ -12,7 +12,7 @@ import abc from typing import List -from pyomo.core.base.constraint import _GeneralConstraintData, Constraint +from pyomo.core.base.constraint import GeneralConstraintData, Constraint from pyomo.core.base.sos import _SOSConstraintData, SOSConstraint from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.param import _ParamData, Param @@ -84,7 +84,7 @@ def add_parameters(self, params: List[_ParamData]): self._add_parameters(params) @abc.abstractmethod - def _add_constraints(self, cons: List[_GeneralConstraintData]): + def _add_constraints(self, cons: List[GeneralConstraintData]): pass def _check_for_new_vars(self, variables: List[_GeneralVarData]): @@ -104,7 +104,7 @@ def _check_to_remove_vars(self, variables: List[_GeneralVarData]): vars_to_remove[v_id] = v self.remove_variables(list(vars_to_remove.values())) - def add_constraints(self, cons: List[_GeneralConstraintData]): + def add_constraints(self, cons: List[GeneralConstraintData]): all_fixed_vars = {} for con in cons: if con in self._named_expressions: @@ -209,10 +209,10 @@ def add_block(self, block): self.set_objective(obj) @abc.abstractmethod - def _remove_constraints(self, cons: List[_GeneralConstraintData]): + def _remove_constraints(self, cons: List[GeneralConstraintData]): pass - def remove_constraints(self, cons: List[_GeneralConstraintData]): + def remove_constraints(self, cons: List[GeneralConstraintData]): self._remove_constraints(cons) for con in cons: if con not in self._named_expressions: @@ -384,7 +384,7 @@ def update(self, timer: HierarchicalTimer = None): for c in self._vars_referenced_by_con.keys(): if c not in current_cons_dict and c not in current_sos_dict: if (c.ctype is Constraint) or ( - c.ctype is None and isinstance(c, _GeneralConstraintData) + c.ctype is None and isinstance(c, GeneralConstraintData) ): old_cons.append(c) else: diff --git a/pyomo/contrib/solver/solution.py b/pyomo/contrib/solver/solution.py index 32e84d2abca..e8c4631e7fd 100644 --- a/pyomo/contrib/solver/solution.py +++ b/pyomo/contrib/solver/solution.py @@ -12,7 +12,7 @@ import abc from typing import Sequence, Dict, Optional, Mapping, NoReturn -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.var import _GeneralVarData from pyomo.core.expr import value from pyomo.common.collections import ComponentMap @@ -67,8 +67,8 @@ def get_primals( """ def get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: """ Returns a dictionary mapping constraint to dual value. @@ -121,8 +121,8 @@ def get_primals(self, vars_to_load=None): return self._solver._get_primals(vars_to_load=vars_to_load) def get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: self._assert_solution_still_valid() return self._solver._get_duals(cons_to_load=cons_to_load) @@ -205,8 +205,8 @@ def get_primals( return res def get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: if self._nl_info is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' diff --git a/pyomo/contrib/solver/tests/unit/test_results.py b/pyomo/contrib/solver/tests/unit/test_results.py index 74404aaba4c..38d6a540836 100644 --- a/pyomo/contrib/solver/tests/unit/test_results.py +++ b/pyomo/contrib/solver/tests/unit/test_results.py @@ -15,7 +15,7 @@ from pyomo.common import unittest from pyomo.common.config import ConfigDict -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.var import _GeneralVarData from pyomo.common.collections import ComponentMap from pyomo.contrib.solver import results @@ -67,8 +67,8 @@ def get_primals( return primals def get_duals( - self, cons_to_load: Optional[Sequence[_GeneralConstraintData]] = None - ) -> Dict[_GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None + ) -> Dict[GeneralConstraintData, float]: if self._duals is None: raise RuntimeError( 'Solution loader does not currently have valid duals. Please ' diff --git a/pyomo/core/base/constraint.py b/pyomo/core/base/constraint.py index cbae828a459..3455d2dde3c 100644 --- a/pyomo/core/base/constraint.py +++ b/pyomo/core/base/constraint.py @@ -285,7 +285,7 @@ class _ConstraintData(metaclass=RenamedClass): __renamed__version__ = '6.7.2.dev0' -class _GeneralConstraintData(ConstraintData): +class GeneralConstraintData(ConstraintData): """ This class defines the data for a single general constraint. @@ -684,6 +684,11 @@ def set_value(self, expr): ) +class _GeneralConstraintData(metaclass=RenamedClass): + __renamed__new_class__ = GeneralConstraintData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register("General constraint expressions.") class Constraint(ActiveIndexedComponent): """ @@ -726,7 +731,7 @@ class Constraint(ActiveIndexedComponent): The class type for the derived subclass """ - _ComponentDataClass = _GeneralConstraintData + _ComponentDataClass = GeneralConstraintData class Infeasible(object): pass @@ -884,14 +889,14 @@ def display(self, prefix="", ostream=None): ) -class ScalarConstraint(_GeneralConstraintData, Constraint): +class ScalarConstraint(GeneralConstraintData, Constraint): """ ScalarConstraint is the implementation representing a single, non-indexed constraint. """ def __init__(self, *args, **kwds): - _GeneralConstraintData.__init__(self, component=self, expr=None) + GeneralConstraintData.__init__(self, component=self, expr=None) Constraint.__init__(self, *args, **kwds) self._index = UnindexedComponent_index @@ -915,7 +920,7 @@ def body(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return _GeneralConstraintData.body.fget(self) + return GeneralConstraintData.body.fget(self) @property def lower(self): @@ -927,7 +932,7 @@ def lower(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return _GeneralConstraintData.lower.fget(self) + return GeneralConstraintData.lower.fget(self) @property def upper(self): @@ -939,7 +944,7 @@ def upper(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return _GeneralConstraintData.upper.fget(self) + return GeneralConstraintData.upper.fget(self) @property def equality(self): @@ -951,7 +956,7 @@ def equality(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return _GeneralConstraintData.equality.fget(self) + return GeneralConstraintData.equality.fget(self) @property def strict_lower(self): @@ -963,7 +968,7 @@ def strict_lower(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return _GeneralConstraintData.strict_lower.fget(self) + return GeneralConstraintData.strict_lower.fget(self) @property def strict_upper(self): @@ -975,7 +980,7 @@ def strict_upper(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return _GeneralConstraintData.strict_upper.fget(self) + return GeneralConstraintData.strict_upper.fget(self) def clear(self): self._data = {} @@ -1040,7 +1045,7 @@ def add(self, index, expr): return self.__setitem__(index, expr) @overload - def __getitem__(self, index) -> _GeneralConstraintData: ... + def __getitem__(self, index) -> GeneralConstraintData: ... __getitem__ = IndexedComponent.__getitem__ # type: ignore diff --git a/pyomo/core/tests/unit/test_con.py b/pyomo/core/tests/unit/test_con.py index 2fa6c24de9c..26ccc7944a7 100644 --- a/pyomo/core/tests/unit/test_con.py +++ b/pyomo/core/tests/unit/test_con.py @@ -44,7 +44,7 @@ InequalityExpression, RangedExpression, ) -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData class TestConstraintCreation(unittest.TestCase): @@ -1074,7 +1074,7 @@ def test_setitem(self): m.c[2] = m.x**2 <= 4 self.assertEqual(len(m.c), 1) self.assertEqual(list(m.c.keys()), [2]) - self.assertIsInstance(m.c[2], _GeneralConstraintData) + self.assertIsInstance(m.c[2], GeneralConstraintData) self.assertEqual(m.c[2].upper, 4) m.c[3] = Constraint.Skip diff --git a/pyomo/core/tests/unit/test_dict_objects.py b/pyomo/core/tests/unit/test_dict_objects.py index 8260f1ae320..a13e0f25ac8 100644 --- a/pyomo/core/tests/unit/test_dict_objects.py +++ b/pyomo/core/tests/unit/test_dict_objects.py @@ -18,7 +18,7 @@ ExpressionDict, ) from pyomo.core.base.var import _GeneralVarData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.core.base.expression import _GeneralExpressionData @@ -375,7 +375,7 @@ def setUp(self): class TestConstraintDict(_TestActiveComponentDictBase, unittest.TestCase): _ctype = ConstraintDict - _cdatatype = _GeneralConstraintData + _cdatatype = GeneralConstraintData def setUp(self): _TestComponentDictBase.setUp(self) diff --git a/pyomo/core/tests/unit/test_list_objects.py b/pyomo/core/tests/unit/test_list_objects.py index 3eb2e279964..e9c1cceb701 100644 --- a/pyomo/core/tests/unit/test_list_objects.py +++ b/pyomo/core/tests/unit/test_list_objects.py @@ -18,7 +18,7 @@ XExpressionList, ) from pyomo.core.base.var import _GeneralVarData -from pyomo.core.base.constraint import _GeneralConstraintData +from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import _GeneralObjectiveData from pyomo.core.base.expression import _GeneralExpressionData @@ -392,7 +392,7 @@ def setUp(self): class TestConstraintList(_TestActiveComponentListBase, unittest.TestCase): _ctype = XConstraintList - _cdatatype = _GeneralConstraintData + _cdatatype = GeneralConstraintData def setUp(self): _TestComponentListBase.setUp(self) diff --git a/pyomo/gdp/tests/common_tests.py b/pyomo/gdp/tests/common_tests.py index e15a7c66d8a..233c3ca9c09 100644 --- a/pyomo/gdp/tests/common_tests.py +++ b/pyomo/gdp/tests/common_tests.py @@ -953,7 +953,7 @@ def check_disjunction_data_target(self, transformation): self.assertIsInstance(transBlock, Block) self.assertIsInstance(transBlock.component("disjunction_xor"), Constraint) self.assertIsInstance( - transBlock.disjunction_xor[2], constraint._GeneralConstraintData + transBlock.disjunction_xor[2], constraint.GeneralConstraintData ) self.assertIsInstance(transBlock.component("relaxedDisjuncts"), Block) self.assertEqual(len(transBlock.relaxedDisjuncts), 3) @@ -963,7 +963,7 @@ def check_disjunction_data_target(self, transformation): m, targets=[m.disjunction[1]] ) self.assertIsInstance( - m.disjunction[1].algebraic_constraint, constraint._GeneralConstraintData + m.disjunction[1].algebraic_constraint, constraint.GeneralConstraintData ) transBlock = m.component("_pyomo_gdp_%s_reformulation_4" % transformation) self.assertIsInstance(transBlock, Block) diff --git a/pyomo/gdp/tests/test_bigm.py b/pyomo/gdp/tests/test_bigm.py index d5dcef3ba58..efef4c5fb1f 100644 --- a/pyomo/gdp/tests/test_bigm.py +++ b/pyomo/gdp/tests/test_bigm.py @@ -1323,8 +1323,8 @@ def test_do_not_transform_deactivated_constraintDatas(self): self.assertEqual(len(cons_list), 2) lb = cons_list[0] ub = cons_list[1] - self.assertIsInstance(lb, constraint._GeneralConstraintData) - self.assertIsInstance(ub, constraint._GeneralConstraintData) + self.assertIsInstance(lb, constraint.GeneralConstraintData) + self.assertIsInstance(ub, constraint.GeneralConstraintData) def checkMs( self, m, disj1c1lb, disj1c1ub, disj1c2lb, disj1c2ub, disj2c1ub, disj2c2ub diff --git a/pyomo/gdp/tests/test_hull.py b/pyomo/gdp/tests/test_hull.py index 55edf244731..6093e01dc25 100644 --- a/pyomo/gdp/tests/test_hull.py +++ b/pyomo/gdp/tests/test_hull.py @@ -1253,11 +1253,11 @@ def check_second_iteration(self, model): orig = model.component("_pyomo_gdp_hull_reformulation") self.assertIsInstance( model.disjunctionList[1].algebraic_constraint, - constraint._GeneralConstraintData, + constraint.GeneralConstraintData, ) self.assertIsInstance( model.disjunctionList[0].algebraic_constraint, - constraint._GeneralConstraintData, + constraint.GeneralConstraintData, ) self.assertFalse(model.disjunctionList[1].active) self.assertFalse(model.disjunctionList[0].active) diff --git a/pyomo/solvers/plugins/solvers/gurobi_persistent.py b/pyomo/solvers/plugins/solvers/gurobi_persistent.py index 4522a2151c3..101a5340ea9 100644 --- a/pyomo/solvers/plugins/solvers/gurobi_persistent.py +++ b/pyomo/solvers/plugins/solvers/gurobi_persistent.py @@ -157,7 +157,7 @@ def set_linear_constraint_attr(self, con, attr, val): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be modified. attr: str @@ -384,7 +384,7 @@ def get_linear_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -431,7 +431,7 @@ def get_quadratic_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -569,7 +569,7 @@ def cbCut(self, con): Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The cut to add """ if not con.active: @@ -647,7 +647,7 @@ def cbLazy(self, con): """ Parameters ---------- - con: pyomo.core.base.constraint._GeneralConstraintData + con: pyomo.core.base.constraint.GeneralConstraintData The lazy constraint to add """ if not con.active: From da96ac3f59b5336be1d805cd8ad60e8b9707b8cd Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:43:27 -0600 Subject: [PATCH 14/83] Renamed _GeneralExpressionData -> GeneralExpressionData --- pyomo/contrib/cp/repn/docplex_writer.py | 6 ++--- .../logical_to_disjunctive_walker.py | 4 +-- pyomo/contrib/fbbt/fbbt.py | 10 +++---- pyomo/contrib/latex_printer/latex_printer.py | 4 +-- pyomo/core/base/component.py | 2 +- pyomo/core/base/expression.py | 27 +++++++++++-------- pyomo/core/base/objective.py | 6 ++--- pyomo/core/tests/unit/test_dict_objects.py | 4 +-- pyomo/core/tests/unit/test_expression.py | 8 +++--- pyomo/core/tests/unit/test_list_objects.py | 4 +-- pyomo/dae/integral.py | 4 +-- pyomo/repn/plugins/nl_writer.py | 2 +- pyomo/repn/standard_repn.py | 6 ++--- 13 files changed, 46 insertions(+), 41 deletions(-) diff --git a/pyomo/contrib/cp/repn/docplex_writer.py b/pyomo/contrib/cp/repn/docplex_writer.py index 510bbf4e398..00b187a585e 100644 --- a/pyomo/contrib/cp/repn/docplex_writer.py +++ b/pyomo/contrib/cp/repn/docplex_writer.py @@ -63,7 +63,7 @@ GeneralBooleanVarData, IndexedBooleanVar, ) -from pyomo.core.base.expression import ScalarExpression, _GeneralExpressionData +from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.param import IndexedParam, ScalarParam, _ParamData from pyomo.core.base.var import ScalarVar, _GeneralVarData, IndexedVar import pyomo.core.expr as EXPR @@ -949,7 +949,7 @@ class LogicalToDoCplex(StreamBasedExpressionVisitor): BeforeExpression: _handle_before_expression_node, AtExpression: _handle_at_expression_node, AlwaysIn: _handle_always_in_node, - _GeneralExpressionData: _handle_named_expression_node, + GeneralExpressionData: _handle_named_expression_node, ScalarExpression: _handle_named_expression_node, } _var_handles = { @@ -966,7 +966,7 @@ class LogicalToDoCplex(StreamBasedExpressionVisitor): ScalarBooleanVar: _before_boolean_var, GeneralBooleanVarData: _before_boolean_var, IndexedBooleanVar: _before_indexed_boolean_var, - _GeneralExpressionData: _before_named_expression, + GeneralExpressionData: _before_named_expression, ScalarExpression: _before_named_expression, IndexedParam: _before_indexed_param, # Because of indirection ScalarParam: _before_param, diff --git a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py index 548078f55f8..b4fb5e26900 100644 --- a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py +++ b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py @@ -27,7 +27,7 @@ value, ) import pyomo.core.base.boolean_var as BV -from pyomo.core.base.expression import ScalarExpression, _GeneralExpressionData +from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.param import ScalarParam, _ParamData from pyomo.core.base.var import ScalarVar, _GeneralVarData from pyomo.gdp.disjunct import AutoLinkedBooleanVar, Disjunct, Disjunction @@ -217,7 +217,7 @@ def _dispatch_atmost(visitor, node, *args): # don't handle them: _before_child_dispatcher[ScalarVar] = _dispatch_var _before_child_dispatcher[_GeneralVarData] = _dispatch_var -_before_child_dispatcher[_GeneralExpressionData] = _dispatch_expression +_before_child_dispatcher[GeneralExpressionData] = _dispatch_expression _before_child_dispatcher[ScalarExpression] = _dispatch_expression diff --git a/pyomo/contrib/fbbt/fbbt.py b/pyomo/contrib/fbbt/fbbt.py index bde33b3caa0..86f94506841 100644 --- a/pyomo/contrib/fbbt/fbbt.py +++ b/pyomo/contrib/fbbt/fbbt.py @@ -26,7 +26,7 @@ from pyomo.core.base.constraint import Constraint from pyomo.core.base.var import Var from pyomo.gdp import Disjunct -from pyomo.core.base.expression import _GeneralExpressionData, ScalarExpression +from pyomo.core.base.expression import GeneralExpressionData, ScalarExpression import logging from pyomo.common.errors import InfeasibleConstraintException, PyomoException from pyomo.common.config import ( @@ -340,7 +340,7 @@ def _prop_bnds_leaf_to_root_GeneralExpression(visitor, node, expr): Parameters ---------- visitor: _FBBTVisitorLeafToRoot - node: pyomo.core.base.expression._GeneralExpressionData + node: pyomo.core.base.expression.GeneralExpressionData expr: GeneralExpression arg """ bnds_dict = visitor.bnds_dict @@ -366,7 +366,7 @@ def _prop_bnds_leaf_to_root_GeneralExpression(visitor, node, expr): numeric_expr.UnaryFunctionExpression: _prop_bnds_leaf_to_root_UnaryFunctionExpression, numeric_expr.LinearExpression: _prop_bnds_leaf_to_root_SumExpression, numeric_expr.AbsExpression: _prop_bnds_leaf_to_root_abs, - _GeneralExpressionData: _prop_bnds_leaf_to_root_GeneralExpression, + GeneralExpressionData: _prop_bnds_leaf_to_root_GeneralExpression, ScalarExpression: _prop_bnds_leaf_to_root_GeneralExpression, }, ) @@ -904,7 +904,7 @@ def _prop_bnds_root_to_leaf_GeneralExpression(node, bnds_dict, feasibility_tol): Parameters ---------- - node: pyomo.core.base.expression._GeneralExpressionData + node: pyomo.core.base.expression.GeneralExpressionData bnds_dict: ComponentMap feasibility_tol: float If the bounds computed on the body of a constraint violate the bounds of the constraint by more than @@ -945,7 +945,7 @@ def _prop_bnds_root_to_leaf_GeneralExpression(node, bnds_dict, feasibility_tol): ) _prop_bnds_root_to_leaf_map[numeric_expr.AbsExpression] = _prop_bnds_root_to_leaf_abs -_prop_bnds_root_to_leaf_map[_GeneralExpressionData] = ( +_prop_bnds_root_to_leaf_map[GeneralExpressionData] = ( _prop_bnds_root_to_leaf_GeneralExpression ) _prop_bnds_root_to_leaf_map[ScalarExpression] = ( diff --git a/pyomo/contrib/latex_printer/latex_printer.py b/pyomo/contrib/latex_printer/latex_printer.py index 42fc9083953..0e9e379eb21 100644 --- a/pyomo/contrib/latex_printer/latex_printer.py +++ b/pyomo/contrib/latex_printer/latex_printer.py @@ -34,7 +34,7 @@ from pyomo.core.expr.visitor import identify_components from pyomo.core.expr.base import ExpressionBase -from pyomo.core.base.expression import ScalarExpression, _GeneralExpressionData +from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.objective import ScalarObjective, _GeneralObjectiveData import pyomo.core.kernel as kernel from pyomo.core.expr.template_expr import ( @@ -399,7 +399,7 @@ def __init__(self): EqualityExpression: handle_equality_node, InequalityExpression: handle_inequality_node, RangedExpression: handle_ranged_inequality_node, - _GeneralExpressionData: handle_named_expression_node, + GeneralExpressionData: handle_named_expression_node, ScalarExpression: handle_named_expression_node, kernel.expression.expression: handle_named_expression_node, kernel.expression.noclone: handle_named_expression_node, diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 1317c928686..6fd82f80ad4 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -803,7 +803,7 @@ class ComponentData(_ComponentBase): # NOTE: This constructor is in-lined in the constructors for the following # classes: BooleanVarData, ConnectorData, ConstraintData, - # _GeneralExpressionData, _LogicalConstraintData, + # GeneralExpressionData, _LogicalConstraintData, # _GeneralLogicalConstraintData, _GeneralObjectiveData, # _ParamData,_GeneralVarData, GeneralBooleanVarData, DisjunctionData, # ArcData, _PortData, _LinearConstraintData, and diff --git a/pyomo/core/base/expression.py b/pyomo/core/base/expression.py index e21613fcbb1..f5376381b2d 100644 --- a/pyomo/core/base/expression.py +++ b/pyomo/core/base/expression.py @@ -148,7 +148,7 @@ class _ExpressionData(metaclass=RenamedClass): __renamed__version__ = '6.7.2.dev0' -class _GeneralExpressionDataImpl(ExpressionData): +class GeneralExpressionDataImpl(ExpressionData): """ An object that defines an expression that is never cloned @@ -240,7 +240,7 @@ def __ipow__(self, other): return numeric_expr._pow_dispatcher[e.__class__, other.__class__](e, other) -class _GeneralExpressionData(_GeneralExpressionDataImpl, ComponentData): +class GeneralExpressionData(GeneralExpressionDataImpl, ComponentData): """ An object that defines an expression that is never cloned @@ -258,12 +258,17 @@ class _GeneralExpressionData(_GeneralExpressionDataImpl, ComponentData): __slots__ = ('_args_',) def __init__(self, expr=None, component=None): - _GeneralExpressionDataImpl.__init__(self, expr) + GeneralExpressionDataImpl.__init__(self, expr) # Inlining ComponentData.__init__ self._component = weakref_ref(component) if (component is not None) else None self._index = NOTSET +class _GeneralExpressionData(metaclass=RenamedClass): + __renamed__new_class__ = GeneralExpressionData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register( "Named expressions that can be used in other expressions." ) @@ -280,7 +285,7 @@ class Expression(IndexedComponent): doc Text describing this component. """ - _ComponentDataClass = _GeneralExpressionData + _ComponentDataClass = GeneralExpressionData # This seems like a copy-paste error, and should be renamed/removed NoConstraint = IndexedComponent.Skip @@ -407,9 +412,9 @@ def construct(self, data=None): timer.report() -class ScalarExpression(_GeneralExpressionData, Expression): +class ScalarExpression(GeneralExpressionData, Expression): def __init__(self, *args, **kwds): - _GeneralExpressionData.__init__(self, expr=None, component=self) + GeneralExpressionData.__init__(self, expr=None, component=self) Expression.__init__(self, *args, **kwds) self._index = UnindexedComponent_index @@ -432,7 +437,7 @@ def __call__(self, exception=True): def expr(self): """Return expression on this expression.""" if self._constructed: - return _GeneralExpressionData.expr.fget(self) + return GeneralExpressionData.expr.fget(self) raise ValueError( "Accessing the expression of Expression '%s' " "before the Expression has been constructed (there " @@ -450,7 +455,7 @@ def clear(self): def set_value(self, expr): """Set the expression on this expression.""" if self._constructed: - return _GeneralExpressionData.set_value(self, expr) + return GeneralExpressionData.set_value(self, expr) raise ValueError( "Setting the expression of Expression '%s' " "before the Expression has been constructed (there " @@ -460,7 +465,7 @@ def set_value(self, expr): def is_constant(self): """A boolean indicating whether this expression is constant.""" if self._constructed: - return _GeneralExpressionData.is_constant(self) + return GeneralExpressionData.is_constant(self) raise ValueError( "Accessing the is_constant flag of Expression '%s' " "before the Expression has been constructed (there " @@ -470,7 +475,7 @@ def is_constant(self): def is_fixed(self): """A boolean indicating whether this expression is fixed.""" if self._constructed: - return _GeneralExpressionData.is_fixed(self) + return GeneralExpressionData.is_fixed(self) raise ValueError( "Accessing the is_fixed flag of Expression '%s' " "before the Expression has been constructed (there " @@ -514,6 +519,6 @@ def add(self, index, expr): """Add an expression with a given index.""" if (type(expr) is tuple) and (expr == Expression.Skip): return None - cdata = _GeneralExpressionData(expr, component=self) + cdata = GeneralExpressionData(expr, component=self) self._data[index] = cdata return cdata diff --git a/pyomo/core/base/objective.py b/pyomo/core/base/objective.py index d259358dcd7..5cd1a1f93eb 100644 --- a/pyomo/core/base/objective.py +++ b/pyomo/core/base/objective.py @@ -28,7 +28,7 @@ UnindexedComponent_set, rule_wrapper, ) -from pyomo.core.base.expression import ExpressionData, _GeneralExpressionDataImpl +from pyomo.core.base.expression import ExpressionData, GeneralExpressionDataImpl from pyomo.core.base.set import Set from pyomo.core.base.initializer import ( Initializer, @@ -120,7 +120,7 @@ def set_sense(self, sense): class _GeneralObjectiveData( - _GeneralExpressionDataImpl, _ObjectiveData, ActiveComponentData + GeneralExpressionDataImpl, _ObjectiveData, ActiveComponentData ): """ This class defines the data for a single objective. @@ -147,7 +147,7 @@ class _GeneralObjectiveData( __slots__ = ("_sense", "_args_") def __init__(self, expr=None, sense=minimize, component=None): - _GeneralExpressionDataImpl.__init__(self, expr) + GeneralExpressionDataImpl.__init__(self, expr) # Inlining ActiveComponentData.__init__ self._component = weakref_ref(component) if (component is not None) else None self._index = NOTSET diff --git a/pyomo/core/tests/unit/test_dict_objects.py b/pyomo/core/tests/unit/test_dict_objects.py index a13e0f25ac8..c82103cefb1 100644 --- a/pyomo/core/tests/unit/test_dict_objects.py +++ b/pyomo/core/tests/unit/test_dict_objects.py @@ -20,7 +20,7 @@ from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import _GeneralObjectiveData -from pyomo.core.base.expression import _GeneralExpressionData +from pyomo.core.base.expression import GeneralExpressionData class _TestComponentDictBase(object): @@ -360,7 +360,7 @@ def setUp(self): class TestExpressionDict(_TestComponentDictBase, unittest.TestCase): _ctype = ExpressionDict - _cdatatype = _GeneralExpressionData + _cdatatype = GeneralExpressionData def setUp(self): _TestComponentDictBase.setUp(self) diff --git a/pyomo/core/tests/unit/test_expression.py b/pyomo/core/tests/unit/test_expression.py index 678df4c01a8..bf3ce0c2179 100644 --- a/pyomo/core/tests/unit/test_expression.py +++ b/pyomo/core/tests/unit/test_expression.py @@ -29,7 +29,7 @@ value, sum_product, ) -from pyomo.core.base.expression import _GeneralExpressionData +from pyomo.core.base.expression import GeneralExpressionData from pyomo.core.expr.compare import compare_expressions, assertExpressionsEqual from pyomo.common.tee import capture_output @@ -515,10 +515,10 @@ def test_implicit_definition(self): model.E = Expression(model.idx) self.assertEqual(len(model.E), 3) expr = model.E[1] - self.assertIs(type(expr), _GeneralExpressionData) + self.assertIs(type(expr), GeneralExpressionData) model.E[1] = None self.assertIs(expr, model.E[1]) - self.assertIs(type(expr), _GeneralExpressionData) + self.assertIs(type(expr), GeneralExpressionData) self.assertIs(expr.expr, None) model.E[1] = 5 self.assertIs(expr, model.E[1]) @@ -537,7 +537,7 @@ def test_explicit_skip_definition(self): model.E[1] = None expr = model.E[1] - self.assertIs(type(expr), _GeneralExpressionData) + self.assertIs(type(expr), GeneralExpressionData) self.assertIs(expr.expr, None) model.E[1] = 5 self.assertIs(expr, model.E[1]) diff --git a/pyomo/core/tests/unit/test_list_objects.py b/pyomo/core/tests/unit/test_list_objects.py index e9c1cceb701..b8e97b464fe 100644 --- a/pyomo/core/tests/unit/test_list_objects.py +++ b/pyomo/core/tests/unit/test_list_objects.py @@ -20,7 +20,7 @@ from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import _GeneralObjectiveData -from pyomo.core.base.expression import _GeneralExpressionData +from pyomo.core.base.expression import GeneralExpressionData class _TestComponentListBase(object): @@ -377,7 +377,7 @@ def setUp(self): class TestExpressionList(_TestComponentListBase, unittest.TestCase): _ctype = XExpressionList - _cdatatype = _GeneralExpressionData + _cdatatype = GeneralExpressionData def setUp(self): _TestComponentListBase.setUp(self) diff --git a/pyomo/dae/integral.py b/pyomo/dae/integral.py index 41114296a93..f767e31f18c 100644 --- a/pyomo/dae/integral.py +++ b/pyomo/dae/integral.py @@ -14,7 +14,7 @@ from pyomo.core.base.indexed_component import rule_wrapper from pyomo.core.base.expression import ( Expression, - _GeneralExpressionData, + GeneralExpressionData, ScalarExpression, IndexedExpression, ) @@ -151,7 +151,7 @@ class ScalarIntegral(ScalarExpression, Integral): """ def __init__(self, *args, **kwds): - _GeneralExpressionData.__init__(self, None, component=self) + GeneralExpressionData.__init__(self, None, component=self) Integral.__init__(self, *args, **kwds) def clear(self): diff --git a/pyomo/repn/plugins/nl_writer.py b/pyomo/repn/plugins/nl_writer.py index 29d841248da..a0dc09e2aa6 100644 --- a/pyomo/repn/plugins/nl_writer.py +++ b/pyomo/repn/plugins/nl_writer.py @@ -70,7 +70,7 @@ ) from pyomo.core.base.component import ActiveComponent from pyomo.core.base.constraint import ConstraintData -from pyomo.core.base.expression import ScalarExpression, _GeneralExpressionData +from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.objective import ( ScalarObjective, _GeneralObjectiveData, diff --git a/pyomo/repn/standard_repn.py b/pyomo/repn/standard_repn.py index 70368dd3d7e..cf2ba334d6c 100644 --- a/pyomo/repn/standard_repn.py +++ b/pyomo/repn/standard_repn.py @@ -21,7 +21,7 @@ from pyomo.core.expr.numvalue import NumericConstant from pyomo.core.base.objective import _GeneralObjectiveData, ScalarObjective from pyomo.core.base import ExpressionData, Expression -from pyomo.core.base.expression import ScalarExpression, _GeneralExpressionData +from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.var import ScalarVar, Var, _GeneralVarData, value from pyomo.core.base.param import ScalarParam, _ParamData from pyomo.core.kernel.expression import expression, noclone @@ -1148,7 +1148,7 @@ def _collect_external_fn(exp, multiplier, idMap, compute_values, verbose, quadra Var: _collect_var, variable: _collect_var, IVariable: _collect_var, - _GeneralExpressionData: _collect_identity, + GeneralExpressionData: _collect_identity, ScalarExpression: _collect_identity, expression: _collect_identity, noclone: _collect_identity, @@ -1547,7 +1547,7 @@ def _linear_collect_pow(exp, multiplier, idMap, compute_values, verbose, coef): Var : _linear_collect_var, variable : _linear_collect_var, IVariable : _linear_collect_var, - _GeneralExpressionData : _linear_collect_identity, + GeneralExpressionData : _linear_collect_identity, ScalarExpression : _linear_collect_identity, expression : _linear_collect_identity, noclone : _linear_collect_identity, From cd5db6637bdd16a72d8260459c6b7757dd6c3cf0 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:43:42 -0600 Subject: [PATCH 15/83] Renamed _GeneralLogicalConstraintData -> GeneralLogicalConstraintData --- pyomo/core/base/component.py | 2 +- pyomo/core/base/logical_constraint.py | 15 ++++++++++----- 2 files changed, 11 insertions(+), 6 deletions(-) diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 6fd82f80ad4..720373db809 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -804,7 +804,7 @@ class ComponentData(_ComponentBase): # NOTE: This constructor is in-lined in the constructors for the following # classes: BooleanVarData, ConnectorData, ConstraintData, # GeneralExpressionData, _LogicalConstraintData, - # _GeneralLogicalConstraintData, _GeneralObjectiveData, + # GeneralLogicalConstraintData, _GeneralObjectiveData, # _ParamData,_GeneralVarData, GeneralBooleanVarData, DisjunctionData, # ArcData, _PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those diff --git a/pyomo/core/base/logical_constraint.py b/pyomo/core/base/logical_constraint.py index 3a7bca75960..9af99c9ce5c 100644 --- a/pyomo/core/base/logical_constraint.py +++ b/pyomo/core/base/logical_constraint.py @@ -99,7 +99,7 @@ def get_value(self): raise NotImplementedError -class _GeneralLogicalConstraintData(_LogicalConstraintData): +class GeneralLogicalConstraintData(_LogicalConstraintData): """ This class defines the data for a single general logical constraint. @@ -173,6 +173,11 @@ def get_value(self): return self._expr +class _GeneralLogicalConstraintData(metaclass=RenamedClass): + __renamed__new_class__ = GeneralLogicalConstraintData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register("General logical constraints.") class LogicalConstraint(ActiveIndexedComponent): """ @@ -215,7 +220,7 @@ class LogicalConstraint(ActiveIndexedComponent): The class type for the derived subclass """ - _ComponentDataClass = _GeneralLogicalConstraintData + _ComponentDataClass = GeneralLogicalConstraintData class Infeasible(object): pass @@ -409,14 +414,14 @@ def _check_skip_add(self, index, expr): return expr -class ScalarLogicalConstraint(_GeneralLogicalConstraintData, LogicalConstraint): +class ScalarLogicalConstraint(GeneralLogicalConstraintData, LogicalConstraint): """ ScalarLogicalConstraint is the implementation representing a single, non-indexed logical constraint. """ def __init__(self, *args, **kwds): - _GeneralLogicalConstraintData.__init__(self, component=self, expr=None) + GeneralLogicalConstraintData.__init__(self, component=self, expr=None) LogicalConstraint.__init__(self, *args, **kwds) self._index = UnindexedComponent_index @@ -436,7 +441,7 @@ def body(self): "an expression. There is currently " "nothing to access." % self.name ) - return _GeneralLogicalConstraintData.body.fget(self) + return GeneralLogicalConstraintData.body.fget(self) raise ValueError( "Accessing the body of logical constraint '%s' " "before the LogicalConstraint has been constructed (there " From 6e9d84cb43e1f327fc230c0711769cea598f3d03 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:45:29 -0600 Subject: [PATCH 16/83] Renamed _GeneralObjectiveData -> GeneralObjectiveData --- pyomo/contrib/appsi/base.py | 8 ++++---- pyomo/contrib/appsi/fbbt.py | 6 +++--- pyomo/contrib/appsi/solvers/cbc.py | 4 ++-- pyomo/contrib/appsi/solvers/cplex.py | 4 ++-- pyomo/contrib/appsi/solvers/ipopt.py | 4 ++-- pyomo/contrib/appsi/writers/lp_writer.py | 4 ++-- pyomo/contrib/appsi/writers/nl_writer.py | 4 ++-- .../contrib/community_detection/detection.py | 4 ++-- pyomo/contrib/latex_printer/latex_printer.py | 4 ++-- pyomo/contrib/solver/base.py | 4 ++-- pyomo/contrib/solver/persistent.py | 6 +++--- pyomo/core/base/component.py | 2 +- pyomo/core/base/objective.py | 19 ++++++++++++------- pyomo/core/tests/unit/test_dict_objects.py | 4 ++-- pyomo/core/tests/unit/test_list_objects.py | 4 ++-- pyomo/repn/plugins/nl_writer.py | 2 +- pyomo/repn/standard_repn.py | 6 +++--- 17 files changed, 47 insertions(+), 42 deletions(-) diff --git a/pyomo/contrib/appsi/base.py b/pyomo/contrib/appsi/base.py index d5982fc72e6..b1538ef1a35 100644 --- a/pyomo/contrib/appsi/base.py +++ b/pyomo/contrib/appsi/base.py @@ -26,7 +26,7 @@ from pyomo.core.base.var import _GeneralVarData, Var from pyomo.core.base.param import _ParamData, Param from pyomo.core.base.block import BlockData, Block -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.collections import ComponentMap from .utils.get_objective import get_objective from .utils.collect_vars_and_named_exprs import collect_vars_and_named_exprs @@ -831,7 +831,7 @@ def remove_block(self, block: BlockData): pass @abc.abstractmethod - def set_objective(self, obj: _GeneralObjectiveData): + def set_objective(self, obj: GeneralObjectiveData): pass @abc.abstractmethod @@ -1054,10 +1054,10 @@ def add_sos_constraints(self, cons: List[_SOSConstraintData]): self._add_sos_constraints(cons) @abc.abstractmethod - def _set_objective(self, obj: _GeneralObjectiveData): + def _set_objective(self, obj: GeneralObjectiveData): pass - def set_objective(self, obj: _GeneralObjectiveData): + def set_objective(self, obj: GeneralObjectiveData): if self._objective is not None: for v in self._vars_referenced_by_obj: self._referenced_variables[id(v)][2] = None diff --git a/pyomo/contrib/appsi/fbbt.py b/pyomo/contrib/appsi/fbbt.py index 121557414b3..ca178a49b00 100644 --- a/pyomo/contrib/appsi/fbbt.py +++ b/pyomo/contrib/appsi/fbbt.py @@ -22,7 +22,7 @@ from pyomo.core.base.param import _ParamData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData -from pyomo.core.base.objective import _GeneralObjectiveData, minimize, maximize +from pyomo.core.base.objective import GeneralObjectiveData, minimize, maximize from pyomo.core.base.block import BlockData from pyomo.core.base import SymbolMap, TextLabeler from pyomo.common.errors import InfeasibleConstraintException @@ -224,13 +224,13 @@ def update_params(self): cp = self._param_map[p_id] cp.value = p.value - def set_objective(self, obj: _GeneralObjectiveData): + def set_objective(self, obj: GeneralObjectiveData): if self._symbolic_solver_labels: if self._objective is not None: self._symbol_map.removeSymbol(self._objective) super().set_objective(obj) - def _set_objective(self, obj: _GeneralObjectiveData): + def _set_objective(self, obj: GeneralObjectiveData): if obj is None: ce = cmodel.Constant(0) sense = 0 diff --git a/pyomo/contrib/appsi/solvers/cbc.py b/pyomo/contrib/appsi/solvers/cbc.py index cc7327df11c..e73d080c02b 100644 --- a/pyomo/contrib/appsi/solvers/cbc.py +++ b/pyomo/contrib/appsi/solvers/cbc.py @@ -30,7 +30,7 @@ from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.timing import HierarchicalTimer from pyomo.common.tee import TeeStream import sys @@ -188,7 +188,7 @@ def remove_constraints(self, cons: List[GeneralConstraintData]): def remove_block(self, block: BlockData): self._writer.remove_block(block) - def set_objective(self, obj: _GeneralObjectiveData): + def set_objective(self, obj: GeneralObjectiveData): self._writer.set_objective(obj) def update_variables(self, variables: List[_GeneralVarData]): diff --git a/pyomo/contrib/appsi/solvers/cplex.py b/pyomo/contrib/appsi/solvers/cplex.py index 222c466fb99..ffca656735e 100644 --- a/pyomo/contrib/appsi/solvers/cplex.py +++ b/pyomo/contrib/appsi/solvers/cplex.py @@ -26,7 +26,7 @@ from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.timing import HierarchicalTimer import sys import time @@ -203,7 +203,7 @@ def remove_constraints(self, cons: List[GeneralConstraintData]): def remove_block(self, block: BlockData): self._writer.remove_block(block) - def set_objective(self, obj: _GeneralObjectiveData): + def set_objective(self, obj: GeneralObjectiveData): self._writer.set_objective(obj) def update_variables(self, variables: List[_GeneralVarData]): diff --git a/pyomo/contrib/appsi/solvers/ipopt.py b/pyomo/contrib/appsi/solvers/ipopt.py index 75ebb10f719..97d76a9ecb1 100644 --- a/pyomo/contrib/appsi/solvers/ipopt.py +++ b/pyomo/contrib/appsi/solvers/ipopt.py @@ -32,7 +32,7 @@ from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.timing import HierarchicalTimer from pyomo.common.tee import TeeStream import sys @@ -252,7 +252,7 @@ def remove_constraints(self, cons: List[GeneralConstraintData]): def remove_block(self, block: BlockData): self._writer.remove_block(block) - def set_objective(self, obj: _GeneralObjectiveData): + def set_objective(self, obj: GeneralObjectiveData): self._writer.set_objective(obj) def update_variables(self, variables: List[_GeneralVarData]): diff --git a/pyomo/contrib/appsi/writers/lp_writer.py b/pyomo/contrib/appsi/writers/lp_writer.py index 39298bd1a61..696b1c16d61 100644 --- a/pyomo/contrib/appsi/writers/lp_writer.py +++ b/pyomo/contrib/appsi/writers/lp_writer.py @@ -13,7 +13,7 @@ from pyomo.core.base.param import _ParamData from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.block import BlockData from pyomo.repn.standard_repn import generate_standard_repn @@ -147,7 +147,7 @@ def update_params(self): cp = self._pyomo_param_to_solver_param_map[p_id] cp.value = p.value - def _set_objective(self, obj: _GeneralObjectiveData): + def _set_objective(self, obj: GeneralObjectiveData): cobj = cmodel.process_lp_objective( self._expr_types, obj, diff --git a/pyomo/contrib/appsi/writers/nl_writer.py b/pyomo/contrib/appsi/writers/nl_writer.py index 3e13ef4077a..33d7c59f08f 100644 --- a/pyomo/contrib/appsi/writers/nl_writer.py +++ b/pyomo/contrib/appsi/writers/nl_writer.py @@ -13,7 +13,7 @@ from pyomo.core.base.param import _ParamData from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.block import BlockData from pyomo.repn.standard_repn import generate_standard_repn @@ -180,7 +180,7 @@ def update_params(self): cp = self._pyomo_param_to_solver_param_map[p_id] cp.value = p.value - def _set_objective(self, obj: _GeneralObjectiveData): + def _set_objective(self, obj: GeneralObjectiveData): if obj is None: const = cmodel.Constant(0) lin_vars = list() diff --git a/pyomo/contrib/community_detection/detection.py b/pyomo/contrib/community_detection/detection.py index 5bf8187a243..af87fa5eb8b 100644 --- a/pyomo/contrib/community_detection/detection.py +++ b/pyomo/contrib/community_detection/detection.py @@ -31,7 +31,7 @@ Objective, ConstraintList, ) -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.expr.visitor import replace_expressions, identify_variables from pyomo.contrib.community_detection.community_graph import generate_model_graph from pyomo.common.dependencies import networkx as nx @@ -750,7 +750,7 @@ def generate_structured_model(self): # Check to see whether 'stored_constraint' is actually an objective (since constraints and objectives # grouped together) if self.with_objective and isinstance( - stored_constraint, (_GeneralObjectiveData, Objective) + stored_constraint, (GeneralObjectiveData, Objective) ): # If the constraint is actually an objective, we add it to the block as an objective new_objective = Objective( diff --git a/pyomo/contrib/latex_printer/latex_printer.py b/pyomo/contrib/latex_printer/latex_printer.py index 0e9e379eb21..5a2365f9544 100644 --- a/pyomo/contrib/latex_printer/latex_printer.py +++ b/pyomo/contrib/latex_printer/latex_printer.py @@ -35,7 +35,7 @@ from pyomo.core.expr.visitor import identify_components from pyomo.core.expr.base import ExpressionBase from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData -from pyomo.core.base.objective import ScalarObjective, _GeneralObjectiveData +from pyomo.core.base.objective import ScalarObjective, GeneralObjectiveData import pyomo.core.kernel as kernel from pyomo.core.expr.template_expr import ( GetItemExpression, @@ -403,7 +403,7 @@ def __init__(self): ScalarExpression: handle_named_expression_node, kernel.expression.expression: handle_named_expression_node, kernel.expression.noclone: handle_named_expression_node, - _GeneralObjectiveData: handle_named_expression_node, + GeneralObjectiveData: handle_named_expression_node, _GeneralVarData: handle_var_node, ScalarObjective: handle_named_expression_node, kernel.objective.objective: handle_named_expression_node, diff --git a/pyomo/contrib/solver/base.py b/pyomo/contrib/solver/base.py index 4b7d8f35ddc..0a12f572e5f 100644 --- a/pyomo/contrib/solver/base.py +++ b/pyomo/contrib/solver/base.py @@ -18,7 +18,7 @@ from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.param import _ParamData from pyomo.core.base.block import BlockData -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.config import document_kwargs_from_configdict, ConfigValue from pyomo.common.errors import ApplicationError from pyomo.common.deprecation import deprecation_warning @@ -276,7 +276,7 @@ def set_instance(self, model): """ @abc.abstractmethod - def set_objective(self, obj: _GeneralObjectiveData): + def set_objective(self, obj: GeneralObjectiveData): """ Set current objective for the model """ diff --git a/pyomo/contrib/solver/persistent.py b/pyomo/contrib/solver/persistent.py index 9b63e05ce46..97a4067e78b 100644 --- a/pyomo/contrib/solver/persistent.py +++ b/pyomo/contrib/solver/persistent.py @@ -16,7 +16,7 @@ from pyomo.core.base.sos import _SOSConstraintData, SOSConstraint from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.param import _ParamData, Param -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.collections import ComponentMap from pyomo.common.timing import HierarchicalTimer from pyomo.core.expr.numvalue import NumericConstant @@ -149,10 +149,10 @@ def add_sos_constraints(self, cons: List[_SOSConstraintData]): self._add_sos_constraints(cons) @abc.abstractmethod - def _set_objective(self, obj: _GeneralObjectiveData): + def _set_objective(self, obj: GeneralObjectiveData): pass - def set_objective(self, obj: _GeneralObjectiveData): + def set_objective(self, obj: GeneralObjectiveData): if self._objective is not None: for v in self._vars_referenced_by_obj: self._referenced_variables[id(v)][2] = None diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 720373db809..1fd30f4212e 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -804,7 +804,7 @@ class ComponentData(_ComponentBase): # NOTE: This constructor is in-lined in the constructors for the following # classes: BooleanVarData, ConnectorData, ConstraintData, # GeneralExpressionData, _LogicalConstraintData, - # GeneralLogicalConstraintData, _GeneralObjectiveData, + # GeneralLogicalConstraintData, GeneralObjectiveData, # _ParamData,_GeneralVarData, GeneralBooleanVarData, DisjunctionData, # ArcData, _PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those diff --git a/pyomo/core/base/objective.py b/pyomo/core/base/objective.py index 5cd1a1f93eb..b89214377ab 100644 --- a/pyomo/core/base/objective.py +++ b/pyomo/core/base/objective.py @@ -119,7 +119,7 @@ def set_sense(self, sense): raise NotImplementedError -class _GeneralObjectiveData( +class GeneralObjectiveData( GeneralExpressionDataImpl, _ObjectiveData, ActiveComponentData ): """ @@ -192,6 +192,11 @@ def set_sense(self, sense): ) +class _GeneralObjectiveData(metaclass=RenamedClass): + __renamed__new_class__ = GeneralObjectiveData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register("Expressions that are minimized or maximized.") class Objective(ActiveIndexedComponent): """ @@ -240,7 +245,7 @@ class Objective(ActiveIndexedComponent): The class type for the derived subclass """ - _ComponentDataClass = _GeneralObjectiveData + _ComponentDataClass = GeneralObjectiveData NoObjective = ActiveIndexedComponent.Skip def __new__(cls, *args, **kwds): @@ -389,14 +394,14 @@ def display(self, prefix="", ostream=None): ) -class ScalarObjective(_GeneralObjectiveData, Objective): +class ScalarObjective(GeneralObjectiveData, Objective): """ ScalarObjective is the implementation representing a single, non-indexed objective. """ def __init__(self, *args, **kwd): - _GeneralObjectiveData.__init__(self, expr=None, component=self) + GeneralObjectiveData.__init__(self, expr=None, component=self) Objective.__init__(self, *args, **kwd) self._index = UnindexedComponent_index @@ -432,7 +437,7 @@ def expr(self): "a sense or expression (there is currently " "no value to return)." % (self.name) ) - return _GeneralObjectiveData.expr.fget(self) + return GeneralObjectiveData.expr.fget(self) raise ValueError( "Accessing the expression of objective '%s' " "before the Objective has been constructed (there " @@ -455,7 +460,7 @@ def sense(self): "a sense or expression (there is currently " "no value to return)." % (self.name) ) - return _GeneralObjectiveData.sense.fget(self) + return GeneralObjectiveData.sense.fget(self) raise ValueError( "Accessing the sense of objective '%s' " "before the Objective has been constructed (there " @@ -498,7 +503,7 @@ def set_sense(self, sense): if self._constructed: if len(self._data) == 0: self._data[None] = self - return _GeneralObjectiveData.set_sense(self, sense) + return GeneralObjectiveData.set_sense(self, sense) raise ValueError( "Setting the sense of objective '%s' " "before the Objective has been constructed (there " diff --git a/pyomo/core/tests/unit/test_dict_objects.py b/pyomo/core/tests/unit/test_dict_objects.py index c82103cefb1..6dd8a21e2b4 100644 --- a/pyomo/core/tests/unit/test_dict_objects.py +++ b/pyomo/core/tests/unit/test_dict_objects.py @@ -19,7 +19,7 @@ ) from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.expression import GeneralExpressionData @@ -384,7 +384,7 @@ def setUp(self): class TestObjectiveDict(_TestActiveComponentDictBase, unittest.TestCase): _ctype = ObjectiveDict - _cdatatype = _GeneralObjectiveData + _cdatatype = GeneralObjectiveData def setUp(self): _TestComponentDictBase.setUp(self) diff --git a/pyomo/core/tests/unit/test_list_objects.py b/pyomo/core/tests/unit/test_list_objects.py index b8e97b464fe..1609f97af90 100644 --- a/pyomo/core/tests/unit/test_list_objects.py +++ b/pyomo/core/tests/unit/test_list_objects.py @@ -19,7 +19,7 @@ ) from pyomo.core.base.var import _GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.objective import _GeneralObjectiveData +from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.expression import GeneralExpressionData @@ -401,7 +401,7 @@ def setUp(self): class TestObjectiveList(_TestActiveComponentListBase, unittest.TestCase): _ctype = XObjectiveList - _cdatatype = _GeneralObjectiveData + _cdatatype = GeneralObjectiveData def setUp(self): _TestComponentListBase.setUp(self) diff --git a/pyomo/repn/plugins/nl_writer.py b/pyomo/repn/plugins/nl_writer.py index a0dc09e2aa6..e1afb5720f3 100644 --- a/pyomo/repn/plugins/nl_writer.py +++ b/pyomo/repn/plugins/nl_writer.py @@ -73,7 +73,7 @@ from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.objective import ( ScalarObjective, - _GeneralObjectiveData, + GeneralObjectiveData, _ObjectiveData, ) from pyomo.core.base.suffix import SuffixFinder diff --git a/pyomo/repn/standard_repn.py b/pyomo/repn/standard_repn.py index cf2ba334d6c..442e4677dbd 100644 --- a/pyomo/repn/standard_repn.py +++ b/pyomo/repn/standard_repn.py @@ -19,7 +19,7 @@ import pyomo.core.expr as EXPR from pyomo.core.expr.numvalue import NumericConstant -from pyomo.core.base.objective import _GeneralObjectiveData, ScalarObjective +from pyomo.core.base.objective import GeneralObjectiveData, ScalarObjective from pyomo.core.base import ExpressionData, Expression from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.var import ScalarVar, Var, _GeneralVarData, value @@ -1154,7 +1154,7 @@ def _collect_external_fn(exp, multiplier, idMap, compute_values, verbose, quadra noclone: _collect_identity, ExpressionData: _collect_identity, Expression: _collect_identity, - _GeneralObjectiveData: _collect_identity, + GeneralObjectiveData: _collect_identity, ScalarObjective: _collect_identity, objective: _collect_identity, } @@ -1553,7 +1553,7 @@ def _linear_collect_pow(exp, multiplier, idMap, compute_values, verbose, coef): noclone : _linear_collect_identity, ExpressionData : _linear_collect_identity, Expression : _linear_collect_identity, - _GeneralObjectiveData : _linear_collect_identity, + GeneralObjectiveData : _linear_collect_identity, ScalarObjective : _linear_collect_identity, objective : _linear_collect_identity, } From aa79e1b4b0e517a28b8bf8360dea9b6a4b91bba3 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:48:14 -0600 Subject: [PATCH 17/83] Renamed _GeneralVarData -> GeneralVarData --- pyomo/contrib/appsi/base.py | 56 +++++++++---------- pyomo/contrib/appsi/fbbt.py | 10 ++-- pyomo/contrib/appsi/solvers/cbc.py | 16 +++--- pyomo/contrib/appsi/solvers/cplex.py | 16 +++--- pyomo/contrib/appsi/solvers/gurobi.py | 12 ++-- pyomo/contrib/appsi/solvers/highs.py | 8 +-- pyomo/contrib/appsi/solvers/ipopt.py | 16 +++--- pyomo/contrib/appsi/solvers/wntr.py | 8 +-- pyomo/contrib/appsi/writers/lp_writer.py | 8 +-- pyomo/contrib/appsi/writers/nl_writer.py | 8 +-- pyomo/contrib/cp/repn/docplex_writer.py | 4 +- .../logical_to_disjunctive_walker.py | 4 +- pyomo/contrib/latex_printer/latex_printer.py | 10 ++-- pyomo/contrib/parmest/utils/scenario_tree.py | 2 +- pyomo/contrib/solver/base.py | 22 ++++---- pyomo/contrib/solver/gurobi.py | 12 ++-- pyomo/contrib/solver/ipopt.py | 6 +- pyomo/contrib/solver/persistent.py | 18 +++--- pyomo/contrib/solver/solution.py | 22 ++++---- .../contrib/solver/tests/unit/test_results.py | 10 ++-- .../trustregion/tests/test_interface.py | 4 +- pyomo/core/base/__init__.py | 2 +- pyomo/core/base/component.py | 2 +- pyomo/core/base/var.py | 15 +++-- pyomo/core/expr/calculus/derivatives.py | 6 +- pyomo/core/tests/transform/test_add_slacks.py | 2 +- pyomo/core/tests/unit/test_dict_objects.py | 6 +- pyomo/core/tests/unit/test_list_objects.py | 6 +- pyomo/core/tests/unit/test_numeric_expr.py | 4 +- pyomo/core/tests/unit/test_reference.py | 12 ++-- pyomo/repn/standard_repn.py | 6 +- .../plugins/solvers/gurobi_persistent.py | 4 +- pyomo/util/report_scaling.py | 4 +- 33 files changed, 173 insertions(+), 168 deletions(-) diff --git a/pyomo/contrib/appsi/base.py b/pyomo/contrib/appsi/base.py index b1538ef1a35..1ce24220bfd 100644 --- a/pyomo/contrib/appsi/base.py +++ b/pyomo/contrib/appsi/base.py @@ -23,7 +23,7 @@ ) from pyomo.core.base.constraint import GeneralConstraintData, Constraint from pyomo.core.base.sos import _SOSConstraintData, SOSConstraint -from pyomo.core.base.var import _GeneralVarData, Var +from pyomo.core.base.var import GeneralVarData, Var from pyomo.core.base.param import _ParamData, Param from pyomo.core.base.block import BlockData, Block from pyomo.core.base.objective import GeneralObjectiveData @@ -180,7 +180,7 @@ def __init__( class SolutionLoaderBase(abc.ABC): def load_vars( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None ) -> NoReturn: """ Load the solution of the primal variables into the value attribute of the variables. @@ -197,8 +197,8 @@ def load_vars( @abc.abstractmethod def get_primals( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: """ Returns a ComponentMap mapping variable to var value. @@ -256,8 +256,8 @@ def get_slacks( ) def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: """ Returns a ComponentMap mapping variable to reduced cost. @@ -303,8 +303,8 @@ def __init__( self._reduced_costs = reduced_costs def get_primals( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if self._primals is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' @@ -353,8 +353,8 @@ def get_slacks( return slacks def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if self._reduced_costs is None: raise RuntimeError( 'Solution loader does not currently have valid reduced costs. Please ' @@ -709,7 +709,7 @@ def is_persistent(self): return True def load_vars( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None ) -> NoReturn: """ Load the solution of the primal variables into the value attribute of the variables. @@ -726,8 +726,8 @@ def load_vars( @abc.abstractmethod def get_primals( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: pass def get_duals( @@ -771,8 +771,8 @@ def get_slacks( ) def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: """ Parameters ---------- @@ -799,7 +799,7 @@ def set_instance(self, model): pass @abc.abstractmethod - def add_variables(self, variables: List[_GeneralVarData]): + def add_variables(self, variables: List[GeneralVarData]): pass @abc.abstractmethod @@ -815,7 +815,7 @@ def add_block(self, block: BlockData): pass @abc.abstractmethod - def remove_variables(self, variables: List[_GeneralVarData]): + def remove_variables(self, variables: List[GeneralVarData]): pass @abc.abstractmethod @@ -835,7 +835,7 @@ def set_objective(self, obj: GeneralObjectiveData): pass @abc.abstractmethod - def update_variables(self, variables: List[_GeneralVarData]): + def update_variables(self, variables: List[GeneralVarData]): pass @abc.abstractmethod @@ -869,8 +869,8 @@ def get_slacks( return self._solver.get_slacks(cons_to_load=cons_to_load) def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: self._assert_solution_still_valid() return self._solver.get_reduced_costs(vars_to_load=vars_to_load) @@ -954,10 +954,10 @@ def set_instance(self, model): self.set_objective(None) @abc.abstractmethod - def _add_variables(self, variables: List[_GeneralVarData]): + def _add_variables(self, variables: List[GeneralVarData]): pass - def add_variables(self, variables: List[_GeneralVarData]): + def add_variables(self, variables: List[GeneralVarData]): for v in variables: if id(v) in self._referenced_variables: raise ValueError( @@ -987,7 +987,7 @@ def add_params(self, params: List[_ParamData]): def _add_constraints(self, cons: List[GeneralConstraintData]): pass - def _check_for_new_vars(self, variables: List[_GeneralVarData]): + def _check_for_new_vars(self, variables: List[GeneralVarData]): new_vars = dict() for v in variables: v_id = id(v) @@ -995,7 +995,7 @@ def _check_for_new_vars(self, variables: List[_GeneralVarData]): new_vars[v_id] = v self.add_variables(list(new_vars.values())) - def _check_to_remove_vars(self, variables: List[_GeneralVarData]): + def _check_to_remove_vars(self, variables: List[GeneralVarData]): vars_to_remove = dict() for v in variables: v_id = id(v) @@ -1174,10 +1174,10 @@ def remove_sos_constraints(self, cons: List[_SOSConstraintData]): del self._vars_referenced_by_con[con] @abc.abstractmethod - def _remove_variables(self, variables: List[_GeneralVarData]): + def _remove_variables(self, variables: List[GeneralVarData]): pass - def remove_variables(self, variables: List[_GeneralVarData]): + def remove_variables(self, variables: List[GeneralVarData]): self._remove_variables(variables) for v in variables: v_id = id(v) @@ -1246,10 +1246,10 @@ def remove_block(self, block): ) @abc.abstractmethod - def _update_variables(self, variables: List[_GeneralVarData]): + def _update_variables(self, variables: List[GeneralVarData]): pass - def update_variables(self, variables: List[_GeneralVarData]): + def update_variables(self, variables: List[GeneralVarData]): for v in variables: self._vars[id(v)] = ( v, diff --git a/pyomo/contrib/appsi/fbbt.py b/pyomo/contrib/appsi/fbbt.py index ca178a49b00..a360d2bce84 100644 --- a/pyomo/contrib/appsi/fbbt.py +++ b/pyomo/contrib/appsi/fbbt.py @@ -18,7 +18,7 @@ ) from .cmodel import cmodel, cmodel_available from typing import List, Optional -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.param import _ParamData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData @@ -121,7 +121,7 @@ def set_instance(self, model, symbolic_solver_labels: Optional[bool] = None): if self._objective is None: self.set_objective(None) - def _add_variables(self, variables: List[_GeneralVarData]): + def _add_variables(self, variables: List[GeneralVarData]): if self._symbolic_solver_labels: set_name = True symbol_map = self._symbol_map @@ -190,7 +190,7 @@ def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): 'IntervalTightener does not support SOS constraints' ) - def _remove_variables(self, variables: List[_GeneralVarData]): + def _remove_variables(self, variables: List[GeneralVarData]): if self._symbolic_solver_labels: for v in variables: self._symbol_map.removeSymbol(v) @@ -205,7 +205,7 @@ def _remove_params(self, params: List[_ParamData]): for p in params: del self._param_map[id(p)] - def _update_variables(self, variables: List[_GeneralVarData]): + def _update_variables(self, variables: List[GeneralVarData]): cmodel.process_pyomo_vars( self._pyomo_expr_types, variables, @@ -304,7 +304,7 @@ def perform_fbbt( self._deactivate_satisfied_cons() return n_iter - def perform_fbbt_with_seed(self, model: BlockData, seed_var: _GeneralVarData): + def perform_fbbt_with_seed(self, model: BlockData, seed_var: GeneralVarData): if model is not self._model: self.set_instance(model) else: diff --git a/pyomo/contrib/appsi/solvers/cbc.py b/pyomo/contrib/appsi/solvers/cbc.py index e73d080c02b..cd5158d905e 100644 --- a/pyomo/contrib/appsi/solvers/cbc.py +++ b/pyomo/contrib/appsi/solvers/cbc.py @@ -26,7 +26,7 @@ import math from pyomo.common.collections import ComponentMap from typing import Optional, Sequence, NoReturn, List, Mapping -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData @@ -164,7 +164,7 @@ def symbol_map(self): def set_instance(self, model): self._writer.set_instance(model) - def add_variables(self, variables: List[_GeneralVarData]): + def add_variables(self, variables: List[GeneralVarData]): self._writer.add_variables(variables) def add_params(self, params: List[_ParamData]): @@ -176,7 +176,7 @@ def add_constraints(self, cons: List[GeneralConstraintData]): def add_block(self, block: BlockData): self._writer.add_block(block) - def remove_variables(self, variables: List[_GeneralVarData]): + def remove_variables(self, variables: List[GeneralVarData]): self._writer.remove_variables(variables) def remove_params(self, params: List[_ParamData]): @@ -191,7 +191,7 @@ def remove_block(self, block: BlockData): def set_objective(self, obj: GeneralObjectiveData): self._writer.set_objective(obj) - def update_variables(self, variables: List[_GeneralVarData]): + def update_variables(self, variables: List[GeneralVarData]): self._writer.update_variables(variables) def update_params(self): @@ -440,8 +440,8 @@ def _check_and_escape_options(): return results def get_primals( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if ( self._last_results_object is None or self._last_results_object.best_feasible_objective is None @@ -477,8 +477,8 @@ def get_duals(self, cons_to_load=None): return {c: self._dual_sol[c] for c in cons_to_load} def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if ( self._last_results_object is None or self._last_results_object.termination_condition diff --git a/pyomo/contrib/appsi/solvers/cplex.py b/pyomo/contrib/appsi/solvers/cplex.py index ffca656735e..cdd699105be 100644 --- a/pyomo/contrib/appsi/solvers/cplex.py +++ b/pyomo/contrib/appsi/solvers/cplex.py @@ -22,7 +22,7 @@ import math from pyomo.common.collections import ComponentMap from typing import Optional, Sequence, NoReturn, List, Mapping, Dict -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData @@ -179,7 +179,7 @@ def update_config(self): def set_instance(self, model): self._writer.set_instance(model) - def add_variables(self, variables: List[_GeneralVarData]): + def add_variables(self, variables: List[GeneralVarData]): self._writer.add_variables(variables) def add_params(self, params: List[_ParamData]): @@ -191,7 +191,7 @@ def add_constraints(self, cons: List[GeneralConstraintData]): def add_block(self, block: BlockData): self._writer.add_block(block) - def remove_variables(self, variables: List[_GeneralVarData]): + def remove_variables(self, variables: List[GeneralVarData]): self._writer.remove_variables(variables) def remove_params(self, params: List[_ParamData]): @@ -206,7 +206,7 @@ def remove_block(self, block: BlockData): def set_objective(self, obj: GeneralObjectiveData): self._writer.set_objective(obj) - def update_variables(self, variables: List[_GeneralVarData]): + def update_variables(self, variables: List[GeneralVarData]): self._writer.update_variables(variables) def update_params(self): @@ -362,8 +362,8 @@ def _postsolve(self, timer: HierarchicalTimer, solve_time): return results def get_primals( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if ( self._cplex_model.solution.get_solution_type() == self._cplex_model.solution.type.none @@ -440,8 +440,8 @@ def get_duals( return res def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if ( self._cplex_model.solution.get_solution_type() == self._cplex_model.solution.type.none diff --git a/pyomo/contrib/appsi/solvers/gurobi.py b/pyomo/contrib/appsi/solvers/gurobi.py index e20168034c6..6da59042a80 100644 --- a/pyomo/contrib/appsi/solvers/gurobi.py +++ b/pyomo/contrib/appsi/solvers/gurobi.py @@ -23,7 +23,7 @@ from pyomo.common.config import ConfigValue, NonNegativeInt from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler -from pyomo.core.base.var import Var, _GeneralVarData +from pyomo.core.base.var import Var, GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.param import _ParamData @@ -458,7 +458,7 @@ def _process_domain_and_bounds( return lb, ub, vtype - def _add_variables(self, variables: List[_GeneralVarData]): + def _add_variables(self, variables: List[GeneralVarData]): var_names = list() vtypes = list() lbs = list() @@ -759,7 +759,7 @@ def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): del self._pyomo_sos_to_solver_sos_map[con] self._needs_updated = True - def _remove_variables(self, variables: List[_GeneralVarData]): + def _remove_variables(self, variables: List[GeneralVarData]): for var in variables: v_id = id(var) if var in self._vars_added_since_update: @@ -774,7 +774,7 @@ def _remove_variables(self, variables: List[_GeneralVarData]): def _remove_params(self, params: List[_ParamData]): pass - def _update_variables(self, variables: List[_GeneralVarData]): + def _update_variables(self, variables: List[GeneralVarData]): for var in variables: var_id = id(var) if var_id not in self._pyomo_var_to_solver_var_map: @@ -1221,7 +1221,7 @@ def set_var_attr(self, var, attr, val): Parameters ---------- - var: pyomo.core.base.var._GeneralVarData + var: pyomo.core.base.var.GeneralVarData The pyomo var for which the corresponding gurobi var attribute should be modified. attr: str @@ -1256,7 +1256,7 @@ def get_var_attr(self, var, attr): Parameters ---------- - var: pyomo.core.base.var._GeneralVarData + var: pyomo.core.base.var.GeneralVarData The pyomo var for which the corresponding gurobi var attribute should be retrieved. attr: str diff --git a/pyomo/contrib/appsi/solvers/highs.py b/pyomo/contrib/appsi/solvers/highs.py index 7773d0624b2..ded0092f38b 100644 --- a/pyomo/contrib/appsi/solvers/highs.py +++ b/pyomo/contrib/appsi/solvers/highs.py @@ -20,7 +20,7 @@ from pyomo.common.log import LogStream from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.param import _ParamData @@ -308,7 +308,7 @@ def _process_domain_and_bounds(self, var_id): return lb, ub, vtype - def _add_variables(self, variables: List[_GeneralVarData]): + def _add_variables(self, variables: List[GeneralVarData]): self._sol = None if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() @@ -493,7 +493,7 @@ def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): 'Highs interface does not support SOS constraints' ) - def _remove_variables(self, variables: List[_GeneralVarData]): + def _remove_variables(self, variables: List[GeneralVarData]): self._sol = None if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() @@ -518,7 +518,7 @@ def _remove_variables(self, variables: List[_GeneralVarData]): def _remove_params(self, params: List[_ParamData]): pass - def _update_variables(self, variables: List[_GeneralVarData]): + def _update_variables(self, variables: List[GeneralVarData]): self._sol = None if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() diff --git a/pyomo/contrib/appsi/solvers/ipopt.py b/pyomo/contrib/appsi/solvers/ipopt.py index 97d76a9ecb1..9ccb58095b1 100644 --- a/pyomo/contrib/appsi/solvers/ipopt.py +++ b/pyomo/contrib/appsi/solvers/ipopt.py @@ -28,7 +28,7 @@ from pyomo.core.expr.numvalue import value from pyomo.core.expr.visitor import replace_expressions from typing import Optional, Sequence, NoReturn, List, Mapping -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import _ParamData @@ -228,7 +228,7 @@ def set_instance(self, model): self._writer.config.symbolic_solver_labels = self.config.symbolic_solver_labels self._writer.set_instance(model) - def add_variables(self, variables: List[_GeneralVarData]): + def add_variables(self, variables: List[GeneralVarData]): self._writer.add_variables(variables) def add_params(self, params: List[_ParamData]): @@ -240,7 +240,7 @@ def add_constraints(self, cons: List[GeneralConstraintData]): def add_block(self, block: BlockData): self._writer.add_block(block) - def remove_variables(self, variables: List[_GeneralVarData]): + def remove_variables(self, variables: List[GeneralVarData]): self._writer.remove_variables(variables) def remove_params(self, params: List[_ParamData]): @@ -255,7 +255,7 @@ def remove_block(self, block: BlockData): def set_objective(self, obj: GeneralObjectiveData): self._writer.set_objective(obj) - def update_variables(self, variables: List[_GeneralVarData]): + def update_variables(self, variables: List[GeneralVarData]): self._writer.update_variables(variables) def update_params(self): @@ -514,8 +514,8 @@ def _apply_solver(self, timer: HierarchicalTimer): return results def get_primals( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if ( self._last_results_object is None or self._last_results_object.best_feasible_objective is None @@ -551,8 +551,8 @@ def get_duals(self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = No return {c: self._dual_sol[c] for c in cons_to_load} def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if ( self._last_results_object is None or self._last_results_object.termination_condition diff --git a/pyomo/contrib/appsi/solvers/wntr.py b/pyomo/contrib/appsi/solvers/wntr.py index c11536e2e6f..7f633161fe1 100644 --- a/pyomo/contrib/appsi/solvers/wntr.py +++ b/pyomo/contrib/appsi/solvers/wntr.py @@ -40,7 +40,7 @@ from pyomo.core.expr.numvalue import native_numeric_types from typing import Dict, Optional, List from pyomo.core.base.block import BlockData -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.param import _ParamData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.common.timing import HierarchicalTimer @@ -239,7 +239,7 @@ def set_instance(self, model): self.add_block(model) - def _add_variables(self, variables: List[_GeneralVarData]): + def _add_variables(self, variables: List[GeneralVarData]): aml = wntr.sim.aml.aml for var in variables: varname = self._symbol_map.getSymbol(var, self._labeler) @@ -302,7 +302,7 @@ def _remove_constraints(self, cons: List[GeneralConstraintData]): del self._pyomo_con_to_solver_con_map[con] self._needs_updated = True - def _remove_variables(self, variables: List[_GeneralVarData]): + def _remove_variables(self, variables: List[GeneralVarData]): for var in variables: v_id = id(var) solver_var = self._pyomo_var_to_solver_var_map[v_id] @@ -322,7 +322,7 @@ def _remove_params(self, params: List[_ParamData]): self._symbol_map.removeSymbol(p) del self._pyomo_param_to_solver_param_map[p_id] - def _update_variables(self, variables: List[_GeneralVarData]): + def _update_variables(self, variables: List[GeneralVarData]): aml = wntr.sim.aml.aml for var in variables: v_id = id(var) diff --git a/pyomo/contrib/appsi/writers/lp_writer.py b/pyomo/contrib/appsi/writers/lp_writer.py index 696b1c16d61..94af5ba7e93 100644 --- a/pyomo/contrib/appsi/writers/lp_writer.py +++ b/pyomo/contrib/appsi/writers/lp_writer.py @@ -11,7 +11,7 @@ from typing import List from pyomo.core.base.param import _ParamData -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.sos import _SOSConstraintData @@ -77,7 +77,7 @@ def set_instance(self, model): if self._objective is None: self.set_objective(None) - def _add_variables(self, variables: List[_GeneralVarData]): + def _add_variables(self, variables: List[GeneralVarData]): cmodel.process_pyomo_vars( self._expr_types, variables, @@ -117,7 +117,7 @@ def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('LP writer does not yet support SOS constraints') - def _remove_variables(self, variables: List[_GeneralVarData]): + def _remove_variables(self, variables: List[GeneralVarData]): for v in variables: cvar = self._pyomo_var_to_solver_var_map.pop(id(v)) del self._solver_var_to_pyomo_var_map[cvar] @@ -128,7 +128,7 @@ def _remove_params(self, params: List[_ParamData]): del self._pyomo_param_to_solver_param_map[id(p)] self._symbol_map.removeSymbol(p) - def _update_variables(self, variables: List[_GeneralVarData]): + def _update_variables(self, variables: List[GeneralVarData]): cmodel.process_pyomo_vars( self._expr_types, variables, diff --git a/pyomo/contrib/appsi/writers/nl_writer.py b/pyomo/contrib/appsi/writers/nl_writer.py index 33d7c59f08f..b7dab1d5a3e 100644 --- a/pyomo/contrib/appsi/writers/nl_writer.py +++ b/pyomo/contrib/appsi/writers/nl_writer.py @@ -11,7 +11,7 @@ from typing import List from pyomo.core.base.param import _ParamData -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.sos import _SOSConstraintData @@ -78,7 +78,7 @@ def set_instance(self, model): self.set_objective(None) self._set_pyomo_amplfunc_env() - def _add_variables(self, variables: List[_GeneralVarData]): + def _add_variables(self, variables: List[GeneralVarData]): if self.config.symbolic_solver_labels: set_name = True symbol_map = self._symbol_map @@ -144,7 +144,7 @@ def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('NL writer does not support SOS constraints') - def _remove_variables(self, variables: List[_GeneralVarData]): + def _remove_variables(self, variables: List[GeneralVarData]): if self.config.symbolic_solver_labels: for v in variables: self._symbol_map.removeSymbol(v) @@ -161,7 +161,7 @@ def _remove_params(self, params: List[_ParamData]): for p in params: del self._pyomo_param_to_solver_param_map[id(p)] - def _update_variables(self, variables: List[_GeneralVarData]): + def _update_variables(self, variables: List[GeneralVarData]): cmodel.process_pyomo_vars( self._expr_types, variables, diff --git a/pyomo/contrib/cp/repn/docplex_writer.py b/pyomo/contrib/cp/repn/docplex_writer.py index 00b187a585e..eb50a543160 100644 --- a/pyomo/contrib/cp/repn/docplex_writer.py +++ b/pyomo/contrib/cp/repn/docplex_writer.py @@ -65,7 +65,7 @@ ) from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.param import IndexedParam, ScalarParam, _ParamData -from pyomo.core.base.var import ScalarVar, _GeneralVarData, IndexedVar +from pyomo.core.base.var import ScalarVar, GeneralVarData, IndexedVar import pyomo.core.expr as EXPR from pyomo.core.expr.visitor import StreamBasedExpressionVisitor, identify_variables from pyomo.core.base import Set, RangeSet @@ -961,7 +961,7 @@ class LogicalToDoCplex(StreamBasedExpressionVisitor): IntervalVarData: _before_interval_var, IndexedIntervalVar: _before_indexed_interval_var, ScalarVar: _before_var, - _GeneralVarData: _before_var, + GeneralVarData: _before_var, IndexedVar: _before_indexed_var, ScalarBooleanVar: _before_boolean_var, GeneralBooleanVarData: _before_boolean_var, diff --git a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py index b4fb5e26900..26b63d020a5 100644 --- a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py +++ b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py @@ -29,7 +29,7 @@ import pyomo.core.base.boolean_var as BV from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.param import ScalarParam, _ParamData -from pyomo.core.base.var import ScalarVar, _GeneralVarData +from pyomo.core.base.var import ScalarVar, GeneralVarData from pyomo.gdp.disjunct import AutoLinkedBooleanVar, Disjunct, Disjunction @@ -216,7 +216,7 @@ def _dispatch_atmost(visitor, node, *args): # for the moment, these are all just so we can get good error messages when we # don't handle them: _before_child_dispatcher[ScalarVar] = _dispatch_var -_before_child_dispatcher[_GeneralVarData] = _dispatch_var +_before_child_dispatcher[GeneralVarData] = _dispatch_var _before_child_dispatcher[GeneralExpressionData] = _dispatch_expression _before_child_dispatcher[ScalarExpression] = _dispatch_expression diff --git a/pyomo/contrib/latex_printer/latex_printer.py b/pyomo/contrib/latex_printer/latex_printer.py index 5a2365f9544..efcd3016dbf 100644 --- a/pyomo/contrib/latex_printer/latex_printer.py +++ b/pyomo/contrib/latex_printer/latex_printer.py @@ -47,7 +47,7 @@ resolve_template, templatize_rule, ) -from pyomo.core.base.var import ScalarVar, _GeneralVarData, IndexedVar +from pyomo.core.base.var import ScalarVar, GeneralVarData, IndexedVar from pyomo.core.base.param import _ParamData, ScalarParam, IndexedParam from pyomo.core.base.set import _SetData, SetOperator from pyomo.core.base.constraint import ScalarConstraint, IndexedConstraint @@ -404,7 +404,7 @@ def __init__(self): kernel.expression.expression: handle_named_expression_node, kernel.expression.noclone: handle_named_expression_node, GeneralObjectiveData: handle_named_expression_node, - _GeneralVarData: handle_var_node, + GeneralVarData: handle_var_node, ScalarObjective: handle_named_expression_node, kernel.objective.objective: handle_named_expression_node, ExternalFunctionExpression: handle_external_function_node, @@ -706,9 +706,9 @@ def latex_printer( temp_comp, temp_indexes = templatize_fcn(pyomo_component) variableList = [] for v in identify_components( - temp_comp, [ScalarVar, _GeneralVarData, IndexedVar] + temp_comp, [ScalarVar, GeneralVarData, IndexedVar] ): - if isinstance(v, _GeneralVarData): + if isinstance(v, GeneralVarData): v_write = v.parent_component() if v_write not in ComponentSet(variableList): variableList.append(v_write) @@ -1275,7 +1275,7 @@ def get_index_names(st, lcm): rep_dict = {} for ky in reversed(list(latex_component_map)): - if isinstance(ky, (pyo.Var, _GeneralVarData)): + if isinstance(ky, (pyo.Var, GeneralVarData)): overwrite_value = latex_component_map[ky] if ky not in existing_components: overwrite_value = overwrite_value.replace('_', '\\_') diff --git a/pyomo/contrib/parmest/utils/scenario_tree.py b/pyomo/contrib/parmest/utils/scenario_tree.py index e71f51877b5..1062e4a2bf4 100644 --- a/pyomo/contrib/parmest/utils/scenario_tree.py +++ b/pyomo/contrib/parmest/utils/scenario_tree.py @@ -25,7 +25,7 @@ def build_vardatalist(self, model, varlist=None): """ - Convert a list of pyomo variables to a list of ScalarVar and _GeneralVarData. If varlist is none, builds a + Convert a list of pyomo variables to a list of ScalarVar and GeneralVarData. If varlist is none, builds a list of all variables in the model. The new list is stored in the vars_to_tighten attribute. By CD Laird Parameters diff --git a/pyomo/contrib/solver/base.py b/pyomo/contrib/solver/base.py index 0a12f572e5f..a935a950819 100644 --- a/pyomo/contrib/solver/base.py +++ b/pyomo/contrib/solver/base.py @@ -15,7 +15,7 @@ import os from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.param import _ParamData from pyomo.core.base.block import BlockData from pyomo.core.base.objective import GeneralObjectiveData @@ -195,7 +195,7 @@ def is_persistent(self): return True def _load_vars( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None ) -> NoReturn: """ Load the solution of the primal variables into the value attribute of the variables. @@ -212,19 +212,19 @@ def _load_vars( @abc.abstractmethod def _get_primals( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: """ Get mapping of variables to primals. Parameters ---------- - vars_to_load : Optional[Sequence[_GeneralVarData]], optional + vars_to_load : Optional[Sequence[GeneralVarData]], optional Which vars to be populated into the map. The default is None. Returns ------- - Mapping[_GeneralVarData, float] + Mapping[GeneralVarData, float] A map of variables to primals. """ raise NotImplementedError( @@ -251,8 +251,8 @@ def _get_duals( raise NotImplementedError(f'{type(self)} does not support the get_duals method') def _get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: """ Parameters ---------- @@ -282,7 +282,7 @@ def set_objective(self, obj: GeneralObjectiveData): """ @abc.abstractmethod - def add_variables(self, variables: List[_GeneralVarData]): + def add_variables(self, variables: List[GeneralVarData]): """ Add variables to the model """ @@ -306,7 +306,7 @@ def add_block(self, block: BlockData): """ @abc.abstractmethod - def remove_variables(self, variables: List[_GeneralVarData]): + def remove_variables(self, variables: List[GeneralVarData]): """ Remove variables from the model """ @@ -330,7 +330,7 @@ def remove_block(self, block: BlockData): """ @abc.abstractmethod - def update_variables(self, variables: List[_GeneralVarData]): + def update_variables(self, variables: List[GeneralVarData]): """ Update variables on the model """ diff --git a/pyomo/contrib/solver/gurobi.py b/pyomo/contrib/solver/gurobi.py index cc95c0c5f0d..353798133db 100644 --- a/pyomo/contrib/solver/gurobi.py +++ b/pyomo/contrib/solver/gurobi.py @@ -22,7 +22,7 @@ from pyomo.common.config import ConfigValue from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.param import _ParamData @@ -438,7 +438,7 @@ def _process_domain_and_bounds( return lb, ub, vtype - def _add_variables(self, variables: List[_GeneralVarData]): + def _add_variables(self, variables: List[GeneralVarData]): var_names = list() vtypes = list() lbs = list() @@ -735,7 +735,7 @@ def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): del self._pyomo_sos_to_solver_sos_map[con] self._needs_updated = True - def _remove_variables(self, variables: List[_GeneralVarData]): + def _remove_variables(self, variables: List[GeneralVarData]): for var in variables: v_id = id(var) if var in self._vars_added_since_update: @@ -750,7 +750,7 @@ def _remove_variables(self, variables: List[_GeneralVarData]): def _remove_parameters(self, params: List[_ParamData]): pass - def _update_variables(self, variables: List[_GeneralVarData]): + def _update_variables(self, variables: List[GeneralVarData]): for var in variables: var_id = id(var) if var_id not in self._pyomo_var_to_solver_var_map: @@ -1151,7 +1151,7 @@ def set_var_attr(self, var, attr, val): Parameters ---------- - var: pyomo.core.base.var._GeneralVarData + var: pyomo.core.base.var.GeneralVarData The pyomo var for which the corresponding gurobi var attribute should be modified. attr: str @@ -1186,7 +1186,7 @@ def get_var_attr(self, var, attr): Parameters ---------- - var: pyomo.core.base.var._GeneralVarData + var: pyomo.core.base.var.GeneralVarData The pyomo var for which the corresponding gurobi var attribute should be retrieved. attr: str diff --git a/pyomo/contrib/solver/ipopt.py b/pyomo/contrib/solver/ipopt.py index 5f601b7a9f7..7111ec6e972 100644 --- a/pyomo/contrib/solver/ipopt.py +++ b/pyomo/contrib/solver/ipopt.py @@ -25,7 +25,7 @@ ) from pyomo.common.tempfiles import TempfileManager from pyomo.common.timing import HierarchicalTimer -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.staleflag import StaleFlagManager from pyomo.repn.plugins.nl_writer import NLWriter, NLWriterInfo from pyomo.contrib.solver.base import SolverBase @@ -80,8 +80,8 @@ def __init__( class IpoptSolutionLoader(SolSolutionLoader): def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if self._nl_info is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' diff --git a/pyomo/contrib/solver/persistent.py b/pyomo/contrib/solver/persistent.py index 97a4067e78b..aeacc9f87c4 100644 --- a/pyomo/contrib/solver/persistent.py +++ b/pyomo/contrib/solver/persistent.py @@ -14,7 +14,7 @@ from pyomo.core.base.constraint import GeneralConstraintData, Constraint from pyomo.core.base.sos import _SOSConstraintData, SOSConstraint -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.param import _ParamData, Param from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.collections import ComponentMap @@ -54,10 +54,10 @@ def set_instance(self, model): self.set_objective(None) @abc.abstractmethod - def _add_variables(self, variables: List[_GeneralVarData]): + def _add_variables(self, variables: List[GeneralVarData]): pass - def add_variables(self, variables: List[_GeneralVarData]): + def add_variables(self, variables: List[GeneralVarData]): for v in variables: if id(v) in self._referenced_variables: raise ValueError( @@ -87,7 +87,7 @@ def add_parameters(self, params: List[_ParamData]): def _add_constraints(self, cons: List[GeneralConstraintData]): pass - def _check_for_new_vars(self, variables: List[_GeneralVarData]): + def _check_for_new_vars(self, variables: List[GeneralVarData]): new_vars = {} for v in variables: v_id = id(v) @@ -95,7 +95,7 @@ def _check_for_new_vars(self, variables: List[_GeneralVarData]): new_vars[v_id] = v self.add_variables(list(new_vars.values())) - def _check_to_remove_vars(self, variables: List[_GeneralVarData]): + def _check_to_remove_vars(self, variables: List[GeneralVarData]): vars_to_remove = {} for v in variables: v_id = id(v) @@ -250,10 +250,10 @@ def remove_sos_constraints(self, cons: List[_SOSConstraintData]): del self._vars_referenced_by_con[con] @abc.abstractmethod - def _remove_variables(self, variables: List[_GeneralVarData]): + def _remove_variables(self, variables: List[GeneralVarData]): pass - def remove_variables(self, variables: List[_GeneralVarData]): + def remove_variables(self, variables: List[GeneralVarData]): self._remove_variables(variables) for v in variables: v_id = id(v) @@ -309,10 +309,10 @@ def remove_block(self, block): ) @abc.abstractmethod - def _update_variables(self, variables: List[_GeneralVarData]): + def _update_variables(self, variables: List[GeneralVarData]): pass - def update_variables(self, variables: List[_GeneralVarData]): + def update_variables(self, variables: List[GeneralVarData]): for v in variables: self._vars[id(v)] = ( v, diff --git a/pyomo/contrib/solver/solution.py b/pyomo/contrib/solver/solution.py index e8c4631e7fd..3f327c1f280 100644 --- a/pyomo/contrib/solver/solution.py +++ b/pyomo/contrib/solver/solution.py @@ -13,7 +13,7 @@ from typing import Sequence, Dict, Optional, Mapping, NoReturn from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.expr import value from pyomo.common.collections import ComponentMap from pyomo.common.errors import DeveloperError @@ -31,7 +31,7 @@ class SolutionLoaderBase(abc.ABC): """ def load_vars( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None ) -> NoReturn: """ Load the solution of the primal variables into the value attribute of the variables. @@ -49,8 +49,8 @@ def load_vars( @abc.abstractmethod def get_primals( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: """ Returns a ComponentMap mapping variable to var value. @@ -86,8 +86,8 @@ def get_duals( raise NotImplementedError(f'{type(self)} does not support the get_duals method') def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: """ Returns a ComponentMap mapping variable to reduced cost. @@ -127,8 +127,8 @@ def get_duals( return self._solver._get_duals(cons_to_load=cons_to_load) def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: self._assert_solution_still_valid() return self._solver._get_reduced_costs(vars_to_load=vars_to_load) @@ -142,7 +142,7 @@ def __init__(self, sol_data: SolFileData, nl_info: NLWriterInfo) -> None: self._nl_info = nl_info def load_vars( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None ) -> NoReturn: if self._nl_info is None: raise RuntimeError( @@ -169,8 +169,8 @@ def load_vars( StaleFlagManager.mark_all_as_stale(delayed=True) def get_primals( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if self._nl_info is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' diff --git a/pyomo/contrib/solver/tests/unit/test_results.py b/pyomo/contrib/solver/tests/unit/test_results.py index 38d6a540836..608af04a0ed 100644 --- a/pyomo/contrib/solver/tests/unit/test_results.py +++ b/pyomo/contrib/solver/tests/unit/test_results.py @@ -16,7 +16,7 @@ from pyomo.common import unittest from pyomo.common.config import ConfigDict from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.common.collections import ComponentMap from pyomo.contrib.solver import results from pyomo.contrib.solver import solution @@ -51,8 +51,8 @@ def __init__( self._reduced_costs = reduced_costs def get_primals( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if self._primals is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' @@ -84,8 +84,8 @@ def get_duals( return duals def get_reduced_costs( - self, vars_to_load: Optional[Sequence[_GeneralVarData]] = None - ) -> Mapping[_GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[GeneralVarData]] = None + ) -> Mapping[GeneralVarData, float]: if self._reduced_costs is None: raise RuntimeError( 'Solution loader does not currently have valid reduced costs. Please ' diff --git a/pyomo/contrib/trustregion/tests/test_interface.py b/pyomo/contrib/trustregion/tests/test_interface.py index 148caceddd1..64f76eb887d 100644 --- a/pyomo/contrib/trustregion/tests/test_interface.py +++ b/pyomo/contrib/trustregion/tests/test_interface.py @@ -33,7 +33,7 @@ cos, SolverFactory, ) -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.expr.numeric_expr import ExternalFunctionExpression from pyomo.core.expr.visitor import identify_variables from pyomo.contrib.trustregion.interface import TRFInterface @@ -158,7 +158,7 @@ def test_replaceExternalFunctionsWithVariables(self): self.assertIsInstance(k, ExternalFunctionExpression) self.assertIn(str(self.interface.model.x[0]), str(k)) self.assertIn(str(self.interface.model.x[1]), str(k)) - self.assertIsInstance(i, _GeneralVarData) + self.assertIsInstance(i, GeneralVarData) self.assertEqual(i, self.interface.data.ef_outputs[1]) for i, k in self.interface.data.basis_expressions.items(): self.assertEqual(k, 0) diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index bb62cb96782..7003cc3d720 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -57,7 +57,7 @@ from pyomo.core.base.check import BuildCheck from pyomo.core.base.set import Set, SetOf, simple_set_rule, RangeSet from pyomo.core.base.param import Param -from pyomo.core.base.var import Var, _VarData, _GeneralVarData, ScalarVar, VarList +from pyomo.core.base.var import Var, _VarData, GeneralVarData, ScalarVar, VarList from pyomo.core.base.boolean_var import ( BooleanVar, BooleanVarData, diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 1fd30f4212e..faf6553be1b 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -805,7 +805,7 @@ class ComponentData(_ComponentBase): # classes: BooleanVarData, ConnectorData, ConstraintData, # GeneralExpressionData, _LogicalConstraintData, # GeneralLogicalConstraintData, GeneralObjectiveData, - # _ParamData,_GeneralVarData, GeneralBooleanVarData, DisjunctionData, + # _ParamData,GeneralVarData, GeneralBooleanVarData, DisjunctionData, # ArcData, _PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those # constructors as well! diff --git a/pyomo/core/base/var.py b/pyomo/core/base/var.py index 856a2dc0237..0e45ad44225 100644 --- a/pyomo/core/base/var.py +++ b/pyomo/core/base/var.py @@ -319,7 +319,7 @@ def free(self): return self.unfix() -class _GeneralVarData(_VarData): +class GeneralVarData(_VarData): """This class defines the data for a single variable.""" __slots__ = ('_value', '_lb', '_ub', '_domain', '_fixed', '_stale') @@ -643,6 +643,11 @@ def _process_bound(self, val, bound_type): return val +class _GeneralVarData(metaclass=RenamedClass): + __renamed__new_class__ = GeneralVarData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register("Decision variables.") class Var(IndexedComponent, IndexedComponent_NDArrayMixin): """A numeric variable, which may be defined over an index. @@ -668,7 +673,7 @@ class Var(IndexedComponent, IndexedComponent_NDArrayMixin): doc (str, optional): Text describing this component. """ - _ComponentDataClass = _GeneralVarData + _ComponentDataClass = GeneralVarData @overload def __new__(cls: Type[Var], *args, **kwargs) -> Union[ScalarVar, IndexedVar]: ... @@ -952,11 +957,11 @@ def _pprint(self): ) -class ScalarVar(_GeneralVarData, Var): +class ScalarVar(GeneralVarData, Var): """A single variable.""" def __init__(self, *args, **kwd): - _GeneralVarData.__init__(self, component=self) + GeneralVarData.__init__(self, component=self) Var.__init__(self, *args, **kwd) self._index = UnindexedComponent_index @@ -1057,7 +1062,7 @@ def domain(self, domain): # between potentially variable GetItemExpression objects and # "constant" GetItemExpression objects. That will need to wait for # the expression rework [JDS; Nov 22]. - def __getitem__(self, args) -> _GeneralVarData: + def __getitem__(self, args) -> GeneralVarData: try: return super().__getitem__(args) except RuntimeError: diff --git a/pyomo/core/expr/calculus/derivatives.py b/pyomo/core/expr/calculus/derivatives.py index ecfdce02fd4..cd23cb16b2c 100644 --- a/pyomo/core/expr/calculus/derivatives.py +++ b/pyomo/core/expr/calculus/derivatives.py @@ -39,11 +39,11 @@ def differentiate(expr, wrt=None, wrt_list=None, mode=Modes.reverse_numeric): ---------- expr: pyomo.core.expr.numeric_expr.NumericExpression The expression to differentiate - wrt: pyomo.core.base.var._GeneralVarData + wrt: pyomo.core.base.var.GeneralVarData If specified, this function will return the derivative with - respect to wrt. wrt is normally a _GeneralVarData, but could + respect to wrt. wrt is normally a GeneralVarData, but could also be a _ParamData. wrt and wrt_list cannot both be specified. - wrt_list: list of pyomo.core.base.var._GeneralVarData + wrt_list: list of pyomo.core.base.var.GeneralVarData If specified, this function will return the derivative with respect to each element in wrt_list. A list will be returned where the values are the derivatives with respect to the diff --git a/pyomo/core/tests/transform/test_add_slacks.py b/pyomo/core/tests/transform/test_add_slacks.py index a74a9b75c4f..d66d6fba79e 100644 --- a/pyomo/core/tests/transform/test_add_slacks.py +++ b/pyomo/core/tests/transform/test_add_slacks.py @@ -330,7 +330,7 @@ def test_error_for_non_constraint_noniterable_target(self): self.assertRaisesRegex( ValueError, "Expected Constraint or list of Constraints.\n\tReceived " - "", + "", TransformationFactory('core.add_slack_variables').apply_to, m, targets=m.indexedVar[1], diff --git a/pyomo/core/tests/unit/test_dict_objects.py b/pyomo/core/tests/unit/test_dict_objects.py index 6dd8a21e2b4..f2c3cad8cc3 100644 --- a/pyomo/core/tests/unit/test_dict_objects.py +++ b/pyomo/core/tests/unit/test_dict_objects.py @@ -17,7 +17,7 @@ ObjectiveDict, ExpressionDict, ) -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.expression import GeneralExpressionData @@ -348,10 +348,10 @@ def test_active(self): class TestVarDict(_TestComponentDictBase, unittest.TestCase): - # Note: the updated _GeneralVarData class only takes an optional + # Note: the updated GeneralVarData class only takes an optional # parent argument (you no longer pass the domain in) _ctype = VarDict - _cdatatype = lambda self, arg: _GeneralVarData() + _cdatatype = lambda self, arg: GeneralVarData() def setUp(self): _TestComponentDictBase.setUp(self) diff --git a/pyomo/core/tests/unit/test_list_objects.py b/pyomo/core/tests/unit/test_list_objects.py index 1609f97af90..fcc83a95a06 100644 --- a/pyomo/core/tests/unit/test_list_objects.py +++ b/pyomo/core/tests/unit/test_list_objects.py @@ -17,7 +17,7 @@ XObjectiveList, XExpressionList, ) -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.expression import GeneralExpressionData @@ -365,10 +365,10 @@ def test_active(self): class TestVarList(_TestComponentListBase, unittest.TestCase): - # Note: the updated _GeneralVarData class only takes an optional + # Note: the updated GeneralVarData class only takes an optional # parent argument (you no longer pass the domain in) _ctype = XVarList - _cdatatype = lambda self, arg: _GeneralVarData() + _cdatatype = lambda self, arg: GeneralVarData() def setUp(self): _TestComponentListBase.setUp(self) diff --git a/pyomo/core/tests/unit/test_numeric_expr.py b/pyomo/core/tests/unit/test_numeric_expr.py index 968b3acb6a4..8e5e43eac9c 100644 --- a/pyomo/core/tests/unit/test_numeric_expr.py +++ b/pyomo/core/tests/unit/test_numeric_expr.py @@ -112,7 +112,7 @@ from pyomo.core.base.label import NumericLabeler from pyomo.core.expr.template_expr import IndexTemplate from pyomo.core.expr import expr_common -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.repn import generate_standard_repn from pyomo.core.expr.numvalue import NumericValue @@ -294,7 +294,7 @@ def value_check(self, exp, val): class TestExpression_EvaluateVarData(TestExpression_EvaluateNumericValue): def create(self, val, domain): - tmp = _GeneralVarData() + tmp = GeneralVarData() tmp.domain = domain tmp.value = val return tmp diff --git a/pyomo/core/tests/unit/test_reference.py b/pyomo/core/tests/unit/test_reference.py index cfd9b99f945..4fa2f4944e9 100644 --- a/pyomo/core/tests/unit/test_reference.py +++ b/pyomo/core/tests/unit/test_reference.py @@ -800,8 +800,8 @@ def test_reference_indexedcomponent_pprint(self): buf.getvalue(), """r : Size=2, Index={1, 2}, ReferenceTo=x Key : Object - 1 : - 2 : + 1 : + 2 : """, ) m.s = Reference(m.x[:, ...], ctype=IndexedComponent) @@ -811,8 +811,8 @@ def test_reference_indexedcomponent_pprint(self): buf.getvalue(), """s : Size=2, Index={1, 2}, ReferenceTo=x[:, ...] Key : Object - 1 : - 2 : + 1 : + 2 : """, ) @@ -1357,8 +1357,8 @@ def test_pprint_nonfinite_sets_ctypeNone(self): 1 IndexedComponent Declarations ref : Size=2, Index=NonNegativeIntegers, ReferenceTo=v Key : Object - 3 : - 5 : + 3 : + 5 : 2 Declarations: v ref """.strip(), diff --git a/pyomo/repn/standard_repn.py b/pyomo/repn/standard_repn.py index 442e4677dbd..907b4a2b115 100644 --- a/pyomo/repn/standard_repn.py +++ b/pyomo/repn/standard_repn.py @@ -22,7 +22,7 @@ from pyomo.core.base.objective import GeneralObjectiveData, ScalarObjective from pyomo.core.base import ExpressionData, Expression from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData -from pyomo.core.base.var import ScalarVar, Var, _GeneralVarData, value +from pyomo.core.base.var import ScalarVar, Var, GeneralVarData, value from pyomo.core.base.param import ScalarParam, _ParamData from pyomo.core.kernel.expression import expression, noclone from pyomo.core.kernel.variable import IVariable, variable @@ -1143,7 +1143,7 @@ def _collect_external_fn(exp, multiplier, idMap, compute_values, verbose, quadra # param.Param : _collect_linear_const, # parameter : _collect_linear_const, NumericConstant: _collect_const, - _GeneralVarData: _collect_var, + GeneralVarData: _collect_var, ScalarVar: _collect_var, Var: _collect_var, variable: _collect_var, @@ -1542,7 +1542,7 @@ def _linear_collect_pow(exp, multiplier, idMap, compute_values, verbose, coef): ##param.ScalarParam : _collect_linear_const, ##param.Param : _collect_linear_const, ##parameter : _collect_linear_const, - _GeneralVarData : _linear_collect_var, + GeneralVarData : _linear_collect_var, ScalarVar : _linear_collect_var, Var : _linear_collect_var, variable : _linear_collect_var, diff --git a/pyomo/solvers/plugins/solvers/gurobi_persistent.py b/pyomo/solvers/plugins/solvers/gurobi_persistent.py index 101a5340ea9..8a81aad3d3e 100644 --- a/pyomo/solvers/plugins/solvers/gurobi_persistent.py +++ b/pyomo/solvers/plugins/solvers/gurobi_persistent.py @@ -192,7 +192,7 @@ def set_var_attr(self, var, attr, val): Parameters ---------- - con: pyomo.core.base.var._GeneralVarData + con: pyomo.core.base.var.GeneralVarData The pyomo var for which the corresponding gurobi var attribute should be modified. attr: str @@ -342,7 +342,7 @@ def get_var_attr(self, var, attr): Parameters ---------- - var: pyomo.core.base.var._GeneralVarData + var: pyomo.core.base.var.GeneralVarData The pyomo var for which the corresponding gurobi var attribute should be retrieved. attr: str diff --git a/pyomo/util/report_scaling.py b/pyomo/util/report_scaling.py index 5ae28baa715..265564bf12d 100644 --- a/pyomo/util/report_scaling.py +++ b/pyomo/util/report_scaling.py @@ -13,7 +13,7 @@ import math from pyomo.core.base.block import BlockData from pyomo.common.collections import ComponentSet -from pyomo.core.base.var import _GeneralVarData +from pyomo.core.base.var import GeneralVarData from pyomo.contrib.fbbt.fbbt import compute_bounds_on_expr from pyomo.core.expr.calculus.diff_with_pyomo import reverse_sd import logging @@ -73,7 +73,7 @@ def _check_coefficients( ): ders = reverse_sd(expr) for _v, _der in ders.items(): - if isinstance(_v, _GeneralVarData): + if isinstance(_v, GeneralVarData): if _v.is_fixed(): continue der_lb, der_ub = compute_bounds_on_expr(_der) From edd83c00ba974bf9d73b95b0e084ed0b63eee71a Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:48:36 -0600 Subject: [PATCH 18/83] Renamed _InfiniteRangeSetData -> InfiniteRangeSetData --- pyomo/core/base/set.py | 23 ++++++++++++++--------- pyomo/core/tests/unit/test_set.py | 4 ++-- 2 files changed, 16 insertions(+), 11 deletions(-) diff --git a/pyomo/core/base/set.py b/pyomo/core/base/set.py index 8db64620d5c..f885dfeaa16 100644 --- a/pyomo/core/base/set.py +++ b/pyomo/core/base/set.py @@ -894,7 +894,7 @@ def _get_continuous_interval(self): @property @deprecated("The 'virtual' attribute is no longer supported", version='5.7') def virtual(self): - return isinstance(self, (_AnySet, SetOperator, _InfiniteRangeSetData)) + return isinstance(self, (_AnySet, SetOperator, InfiniteRangeSetData)) @virtual.setter def virtual(self, value): @@ -2608,7 +2608,7 @@ def ord(self, item): ############################################################################ -class _InfiniteRangeSetData(_SetData): +class InfiniteRangeSetData(_SetData): """Data class for a infinite set. This Set implements an interface to an *infinite set* defined by one @@ -2653,8 +2653,13 @@ def ranges(self): return iter(self._ranges) +class _InfiniteRangeSetData(metaclass=RenamedClass): + __renamed__new_class__ = InfiniteRangeSetData + __renamed__version__ = '6.7.2.dev0' + + class FiniteRangeSetData( - _SortedSetMixin, _OrderedSetMixin, _FiniteSetMixin, _InfiniteRangeSetData + _SortedSetMixin, _OrderedSetMixin, _FiniteSetMixin, InfiniteRangeSetData ): __slots__ = () @@ -2754,11 +2759,11 @@ def ord(self, item): ) # We must redefine ranges(), bounds(), and domain so that we get the - # _InfiniteRangeSetData version and not the one from + # InfiniteRangeSetData version and not the one from # _FiniteSetMixin. - bounds = _InfiniteRangeSetData.bounds - ranges = _InfiniteRangeSetData.ranges - domain = _InfiniteRangeSetData.domain + bounds = InfiniteRangeSetData.bounds + ranges = InfiniteRangeSetData.ranges + domain = InfiniteRangeSetData.domain class _FiniteRangeSetData(metaclass=RenamedClass): @@ -3228,9 +3233,9 @@ def _pprint(self): ) -class InfiniteScalarRangeSet(_InfiniteRangeSetData, RangeSet): +class InfiniteScalarRangeSet(InfiniteRangeSetData, RangeSet): def __init__(self, *args, **kwds): - _InfiniteRangeSetData.__init__(self, component=self) + InfiniteRangeSetData.__init__(self, component=self) RangeSet.__init__(self, *args, **kwds) self._index = UnindexedComponent_index diff --git a/pyomo/core/tests/unit/test_set.py b/pyomo/core/tests/unit/test_set.py index a9b9fb9469b..d669bb38f3b 100644 --- a/pyomo/core/tests/unit/test_set.py +++ b/pyomo/core/tests/unit/test_set.py @@ -61,7 +61,7 @@ InfiniteSetOf, RangeSet, FiniteRangeSetData, - _InfiniteRangeSetData, + InfiniteRangeSetData, FiniteScalarRangeSet, InfiniteScalarRangeSet, AbstractFiniteScalarRangeSet, @@ -1297,7 +1297,7 @@ def test_is_functions(self): self.assertFalse(i.isdiscrete()) self.assertFalse(i.isfinite()) self.assertFalse(i.isordered()) - self.assertIsInstance(i, _InfiniteRangeSetData) + self.assertIsInstance(i, InfiniteRangeSetData) def test_pprint(self): m = ConcreteModel() From b5c9dbaee26359c842dfeee3d8b962da81a7f513 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:48:49 -0600 Subject: [PATCH 19/83] Renamed _InsertionOrderSetData -> InsertionOrderSetData --- pyomo/core/base/set.py | 23 +++++++++++++-------- pyomo/core/tests/unit/test_set.py | 8 +++---- pyomo/core/tests/unit/test_template_expr.py | 2 +- 3 files changed, 19 insertions(+), 14 deletions(-) diff --git a/pyomo/core/base/set.py b/pyomo/core/base/set.py index f885dfeaa16..c0e9491ed1c 100644 --- a/pyomo/core/base/set.py +++ b/pyomo/core/base/set.py @@ -1642,9 +1642,9 @@ class _OrderedSetData(_OrderedSetMixin, FiniteSetData): In older Pyomo terms, this defines a "concrete" ordered set - that is, a set that "owns" the list of set members. While this class actually implements a set ordered by insertion order, we make the "official" - _InsertionOrderSetData an empty derivative class, so that + InsertionOrderSetData an empty derivative class, so that - issubclass(_SortedSetData, _InsertionOrderSetData) == False + issubclass(_SortedSetData, InsertionOrderSetData) == False Constructor Arguments: component The Set object that owns this data. @@ -1735,7 +1735,7 @@ def ord(self, item): raise ValueError("%s.ord(x): x not in %s" % (self.name, self.name)) -class _InsertionOrderSetData(_OrderedSetData): +class InsertionOrderSetData(_OrderedSetData): """ This class defines the data for a ordered set where the items are ordered in insertion order (similar to Python's OrderedSet. @@ -1756,7 +1756,7 @@ def set_value(self, val): "This WILL potentially lead to nondeterministic behavior " "in Pyomo" % (type(val).__name__,) ) - super(_InsertionOrderSetData, self).set_value(val) + super(InsertionOrderSetData, self).set_value(val) def update(self, values): if type(values) in Set._UnorderedInitializers: @@ -1766,7 +1766,12 @@ def update(self, values): "This WILL potentially lead to nondeterministic behavior " "in Pyomo" % (type(values).__name__,) ) - super(_InsertionOrderSetData, self).update(values) + super(InsertionOrderSetData, self).update(values) + + +class _InsertionOrderSetData(metaclass=RenamedClass): + __renamed__new_class__ = InsertionOrderSetData + __renamed__version__ = '6.7.2.dev0' class _SortedSetMixin(object): @@ -2035,7 +2040,7 @@ def __new__(cls, *args, **kwds): else: newObj = super(Set, cls).__new__(IndexedSet) if ordered is Set.InsertionOrder: - newObj._ComponentDataClass = _InsertionOrderSetData + newObj._ComponentDataClass = InsertionOrderSetData elif ordered is Set.SortedOrder: newObj._ComponentDataClass = _SortedSetData else: @@ -2363,7 +2368,7 @@ def _pprint(self): _ordered = "Sorted" else: _ordered = "{user}" - elif issubclass(_refClass, _InsertionOrderSetData): + elif issubclass(_refClass, InsertionOrderSetData): _ordered = "Insertion" return ( [ @@ -2405,13 +2410,13 @@ class FiniteSimpleSet(metaclass=RenamedClass): __renamed__version__ = '6.0' -class OrderedScalarSet(_ScalarOrderedSetMixin, _InsertionOrderSetData, Set): +class OrderedScalarSet(_ScalarOrderedSetMixin, InsertionOrderSetData, Set): def __init__(self, **kwds): # In case someone inherits from us, we will provide a rational # default for the "ordered" flag kwds.setdefault('ordered', Set.InsertionOrder) - _InsertionOrderSetData.__init__(self, component=self) + InsertionOrderSetData.__init__(self, component=self) Set.__init__(self, **kwds) diff --git a/pyomo/core/tests/unit/test_set.py b/pyomo/core/tests/unit/test_set.py index d669bb38f3b..38870d5213e 100644 --- a/pyomo/core/tests/unit/test_set.py +++ b/pyomo/core/tests/unit/test_set.py @@ -83,7 +83,7 @@ SetProduct_OrderedSet, _SetData, FiniteSetData, - _InsertionOrderSetData, + InsertionOrderSetData, _SortedSetData, _FiniteSetMixin, _OrderedSetMixin, @@ -4155,9 +4155,9 @@ def test_indexed_set(self): self.assertTrue(m.I[1].isordered()) self.assertTrue(m.I[2].isordered()) self.assertTrue(m.I[3].isordered()) - self.assertIs(type(m.I[1]), _InsertionOrderSetData) - self.assertIs(type(m.I[2]), _InsertionOrderSetData) - self.assertIs(type(m.I[3]), _InsertionOrderSetData) + self.assertIs(type(m.I[1]), InsertionOrderSetData) + self.assertIs(type(m.I[2]), InsertionOrderSetData) + self.assertIs(type(m.I[3]), InsertionOrderSetData) self.assertEqual(m.I.data(), {1: (4, 2, 5), 2: (4, 2, 5), 3: (4, 2, 5)}) # Explicit (constant) construction diff --git a/pyomo/core/tests/unit/test_template_expr.py b/pyomo/core/tests/unit/test_template_expr.py index 4f255e3567a..e6bd9d98a7d 100644 --- a/pyomo/core/tests/unit/test_template_expr.py +++ b/pyomo/core/tests/unit/test_template_expr.py @@ -127,7 +127,7 @@ def test_template_scalar_with_set(self): # Note that structural expressions do not implement polynomial_degree with self.assertRaisesRegex( AttributeError, - "'_InsertionOrderSetData' object has " "no attribute 'polynomial_degree'", + "'InsertionOrderSetData' object has " "no attribute 'polynomial_degree'", ): e.polynomial_degree() self.assertEqual(str(e), "s[{I}]") From d4d522a4e9b38b17f1944cdbab4292da2b11a220 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:49:48 -0600 Subject: [PATCH 20/83] Renamed _LogicalConstraintData -> LogicalConstraintData --- pyomo/core/base/__init__.py | 2 +- pyomo/core/base/component.py | 2 +- pyomo/core/base/logical_constraint.py | 13 +++++++++---- 3 files changed, 11 insertions(+), 6 deletions(-) diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 7003cc3d720..7d1bd1401f7 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -75,7 +75,7 @@ from pyomo.core.base.logical_constraint import ( LogicalConstraint, LogicalConstraintList, - _LogicalConstraintData, + LogicalConstraintData, ) from pyomo.core.base.objective import ( simple_objective_rule, diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index faf6553be1b..341cd1506ff 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -803,7 +803,7 @@ class ComponentData(_ComponentBase): # NOTE: This constructor is in-lined in the constructors for the following # classes: BooleanVarData, ConnectorData, ConstraintData, - # GeneralExpressionData, _LogicalConstraintData, + # GeneralExpressionData, LogicalConstraintData, # GeneralLogicalConstraintData, GeneralObjectiveData, # _ParamData,GeneralVarData, GeneralBooleanVarData, DisjunctionData, # ArcData, _PortData, _LinearConstraintData, and diff --git a/pyomo/core/base/logical_constraint.py b/pyomo/core/base/logical_constraint.py index 9af99c9ce5c..23a422705df 100644 --- a/pyomo/core/base/logical_constraint.py +++ b/pyomo/core/base/logical_constraint.py @@ -42,7 +42,7 @@ """ -class _LogicalConstraintData(ActiveComponentData): +class LogicalConstraintData(ActiveComponentData): """ This class defines the data for a single logical constraint. @@ -99,7 +99,12 @@ def get_value(self): raise NotImplementedError -class GeneralLogicalConstraintData(_LogicalConstraintData): +class _LogicalConstraintData(metaclass=RenamedClass): + __renamed__new_class__ = LogicalConstraintData + __renamed__version__ = '6.7.2.dev0' + + +class GeneralLogicalConstraintData(LogicalConstraintData): """ This class defines the data for a single general logical constraint. @@ -123,7 +128,7 @@ def __init__(self, expr=None, component=None): # # These lines represent in-lining of the # following constructors: - # - _LogicalConstraintData, + # - LogicalConstraintData, # - ActiveComponentData # - ComponentData self._component = weakref_ref(component) if (component is not None) else None @@ -455,7 +460,7 @@ def body(self): # currently in place). So during initialization only, we will # treat them as "indexed" objects where things like # True are managed. But after that they will behave - # like _LogicalConstraintData objects where set_value expects + # like LogicalConstraintData objects where set_value expects # a valid expression or None. # From c37fc4fb13794b35e94e86b3a185494d2383f432 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:50:02 -0600 Subject: [PATCH 21/83] Renamed _ObjectiveData -> ObjectiveData --- pyomo/core/base/__init__.py | 2 +- pyomo/core/base/objective.py | 11 ++++++++--- pyomo/core/beta/dict_objects.py | 4 ++-- pyomo/core/beta/list_objects.py | 4 ++-- pyomo/core/plugins/transform/scaling.py | 4 ++-- pyomo/core/tests/unit/test_obj.py | 2 +- pyomo/core/tests/unit/test_suffix.py | 4 ++-- pyomo/repn/plugins/nl_writer.py | 6 +++--- 8 files changed, 21 insertions(+), 16 deletions(-) diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 7d1bd1401f7..408cf16c00e 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -82,7 +82,7 @@ simple_objectivelist_rule, Objective, ObjectiveList, - _ObjectiveData, + ObjectiveData, ) from pyomo.core.base.connector import Connector from pyomo.core.base.sos import SOSConstraint diff --git a/pyomo/core/base/objective.py b/pyomo/core/base/objective.py index b89214377ab..58cb198e1ae 100644 --- a/pyomo/core/base/objective.py +++ b/pyomo/core/base/objective.py @@ -86,7 +86,7 @@ def O_rule(model, i, j): # -class _ObjectiveData(ExpressionData): +class ObjectiveData(ExpressionData): """ This class defines the data for a single objective. @@ -119,8 +119,13 @@ def set_sense(self, sense): raise NotImplementedError +class _ObjectiveData(metaclass=RenamedClass): + __renamed__new_class__ = ObjectiveData + __renamed__version__ = '6.7.2.dev0' + + class GeneralObjectiveData( - GeneralExpressionDataImpl, _ObjectiveData, ActiveComponentData + GeneralExpressionDataImpl, ObjectiveData, ActiveComponentData ): """ This class defines the data for a single objective. @@ -479,7 +484,7 @@ def sense(self, sense): # currently in place). So during initialization only, we will # treat them as "indexed" objects where things like # Objective.Skip are managed. But after that they will behave - # like _ObjectiveData objects where set_value does not handle + # like ObjectiveData objects where set_value does not handle # Objective.Skip but expects a valid expression or None # diff --git a/pyomo/core/beta/dict_objects.py b/pyomo/core/beta/dict_objects.py index 2b23d81e91a..7c44166f189 100644 --- a/pyomo/core/beta/dict_objects.py +++ b/pyomo/core/beta/dict_objects.py @@ -16,7 +16,7 @@ from pyomo.core.base.set_types import Any from pyomo.core.base.var import IndexedVar, _VarData from pyomo.core.base.constraint import IndexedConstraint, ConstraintData -from pyomo.core.base.objective import IndexedObjective, _ObjectiveData +from pyomo.core.base.objective import IndexedObjective, ObjectiveData from pyomo.core.base.expression import IndexedExpression, ExpressionData from collections.abc import MutableMapping @@ -202,7 +202,7 @@ def __init__(self, *args, **kwds): # Constructor for ComponentDict needs to # go last in order to handle any initialization # iterable as an argument - ComponentDict.__init__(self, _ObjectiveData, *args, **kwds) + ComponentDict.__init__(self, ObjectiveData, *args, **kwds) class ExpressionDict(ComponentDict, IndexedExpression): diff --git a/pyomo/core/beta/list_objects.py b/pyomo/core/beta/list_objects.py index dd199eb70cd..d10a30e18e2 100644 --- a/pyomo/core/beta/list_objects.py +++ b/pyomo/core/beta/list_objects.py @@ -16,7 +16,7 @@ from pyomo.core.base.set_types import Any from pyomo.core.base.var import IndexedVar, _VarData from pyomo.core.base.constraint import IndexedConstraint, ConstraintData -from pyomo.core.base.objective import IndexedObjective, _ObjectiveData +from pyomo.core.base.objective import IndexedObjective, ObjectiveData from pyomo.core.base.expression import IndexedExpression, ExpressionData from collections.abc import MutableSequence @@ -250,7 +250,7 @@ def __init__(self, *args, **kwds): # Constructor for ComponentList needs to # go last in order to handle any initialization # iterable as an argument - ComponentList.__init__(self, _ObjectiveData, *args, **kwds) + ComponentList.__init__(self, ObjectiveData, *args, **kwds) class XExpressionList(ComponentList, IndexedExpression): diff --git a/pyomo/core/plugins/transform/scaling.py b/pyomo/core/plugins/transform/scaling.py index 6b83a2378d1..ef418f094ae 100644 --- a/pyomo/core/plugins/transform/scaling.py +++ b/pyomo/core/plugins/transform/scaling.py @@ -16,7 +16,7 @@ Constraint, Objective, ConstraintData, - _ObjectiveData, + ObjectiveData, Suffix, value, ) @@ -226,7 +226,7 @@ def _apply_to(self, model, rename=True): else: c.set_value((lower, body, upper)) - elif isinstance(c, _ObjectiveData): + elif isinstance(c, ObjectiveData): c.expr = scaling_factor * replace_expressions( expr=c.expr, substitution_map=variable_substitution_dict, diff --git a/pyomo/core/tests/unit/test_obj.py b/pyomo/core/tests/unit/test_obj.py index 3c8a05f7058..dc2e320e63b 100644 --- a/pyomo/core/tests/unit/test_obj.py +++ b/pyomo/core/tests/unit/test_obj.py @@ -78,7 +78,7 @@ def test_empty_singleton(self): # Even though we construct a ScalarObjective, # if it is not initialized that means it is "empty" # and we should encounter errors when trying to access the - # _ObjectiveData interface methods until we assign + # ObjectiveData interface methods until we assign # something to the objective. # self.assertEqual(a._constructed, True) diff --git a/pyomo/core/tests/unit/test_suffix.py b/pyomo/core/tests/unit/test_suffix.py index 9597bad7571..70f028a3eff 100644 --- a/pyomo/core/tests/unit/test_suffix.py +++ b/pyomo/core/tests/unit/test_suffix.py @@ -1567,7 +1567,7 @@ def test_clone_ObjectiveArray(self): self.assertEqual(inst.junk.get(model.obj[1]), None) self.assertEqual(inst.junk.get(inst.obj[1]), 1.0) - def test_clone_ObjectiveData(self): + def test_cloneObjectiveData(self): model = ConcreteModel() model.x = Var([1, 2, 3], dense=True) model.obj = Objective([1, 2, 3], rule=lambda model, i: model.x[i]) @@ -1725,7 +1725,7 @@ def test_pickle_ObjectiveArray(self): self.assertEqual(inst.junk.get(model.obj[1]), None) self.assertEqual(inst.junk.get(inst.obj[1]), 1.0) - def test_pickle_ObjectiveData(self): + def test_pickleObjectiveData(self): model = ConcreteModel() model.x = Var([1, 2, 3], dense=True) model.obj = Objective([1, 2, 3], rule=simple_obj_rule) diff --git a/pyomo/repn/plugins/nl_writer.py b/pyomo/repn/plugins/nl_writer.py index e1afb5720f3..c010cee5e54 100644 --- a/pyomo/repn/plugins/nl_writer.py +++ b/pyomo/repn/plugins/nl_writer.py @@ -74,7 +74,7 @@ from pyomo.core.base.objective import ( ScalarObjective, GeneralObjectiveData, - _ObjectiveData, + ObjectiveData, ) from pyomo.core.base.suffix import SuffixFinder from pyomo.core.base.var import _VarData @@ -139,7 +139,7 @@ class NLWriterInfo(object): The list of (active) Pyomo model constraints in the order written to the NL file - objectives: List[_ObjectiveData] + objectives: List[ObjectiveData] The list of (active) Pyomo model objectives in the order written to the NL file @@ -466,7 +466,7 @@ def compile(self, column_order, row_order, obj_order, model_id): self.obj[obj_order[_id]] = val elif _id == model_id: self.prob[0] = val - elif isinstance(obj, (_VarData, ConstraintData, _ObjectiveData)): + elif isinstance(obj, (_VarData, ConstraintData, ObjectiveData)): missing_component_data.add(obj) elif isinstance(obj, (Var, Constraint, Objective)): # Expand this indexed component to store the From 4127432baf064f55d2f09d7c264109734e70f4b7 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:50:05 -0600 Subject: [PATCH 22/83] Renamed _OrderedSetData -> OrderedSetData --- pyomo/core/base/set.py | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/pyomo/core/base/set.py b/pyomo/core/base/set.py index c0e9491ed1c..c7a7edc8e4b 100644 --- a/pyomo/core/base/set.py +++ b/pyomo/core/base/set.py @@ -1301,7 +1301,7 @@ class FiniteSetData(_FiniteSetMixin, _SetData): def __init__(self, component): _SetData.__init__(self, component=component) - # Derived classes (like _OrderedSetData) may want to change the + # Derived classes (like OrderedSetData) may want to change the # storage if not hasattr(self, '_values'): self._values = set() @@ -1635,7 +1635,7 @@ def _to_0_based_index(self, item): ) -class _OrderedSetData(_OrderedSetMixin, FiniteSetData): +class OrderedSetData(_OrderedSetMixin, FiniteSetData): """ This class defines the base class for an ordered set of concrete data. @@ -1735,7 +1735,12 @@ def ord(self, item): raise ValueError("%s.ord(x): x not in %s" % (self.name, self.name)) -class InsertionOrderSetData(_OrderedSetData): +class _OrderedSetData(metaclass=RenamedClass): + __renamed__new_class__ = OrderedSetData + __renamed__version__ = '6.7.2.dev0' + + +class InsertionOrderSetData(OrderedSetData): """ This class defines the data for a ordered set where the items are ordered in insertion order (similar to Python's OrderedSet. @@ -1786,7 +1791,7 @@ def sorted_iter(self): return iter(self) -class _SortedSetData(_SortedSetMixin, _OrderedSetData): +class _SortedSetData(_SortedSetMixin, OrderedSetData): """ This class defines the data for a sorted set. @@ -1801,7 +1806,7 @@ class _SortedSetData(_SortedSetMixin, _OrderedSetData): def __init__(self, component): # An empty set is sorted... self._is_sorted = True - _OrderedSetData.__init__(self, component=component) + OrderedSetData.__init__(self, component=component) def _iter_impl(self): """ From ec3f121f81a4f52295caab029d5bfb5e826c569e Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:51:57 -0600 Subject: [PATCH 23/83] Renamed _ParamData -> ParamData --- pyomo/contrib/appsi/base.py | 14 ++++---- pyomo/contrib/appsi/fbbt.py | 6 ++-- pyomo/contrib/appsi/solvers/cbc.py | 6 ++-- pyomo/contrib/appsi/solvers/cplex.py | 6 ++-- pyomo/contrib/appsi/solvers/gurobi.py | 6 ++-- pyomo/contrib/appsi/solvers/highs.py | 6 ++-- pyomo/contrib/appsi/solvers/ipopt.py | 6 ++-- pyomo/contrib/appsi/solvers/wntr.py | 6 ++-- pyomo/contrib/appsi/writers/lp_writer.py | 6 ++-- pyomo/contrib/appsi/writers/nl_writer.py | 6 ++-- pyomo/contrib/cp/repn/docplex_writer.py | 4 +-- .../logical_to_disjunctive_walker.py | 4 +-- pyomo/contrib/latex_printer/latex_printer.py | 12 +++---- pyomo/contrib/pyros/config.py | 8 ++--- pyomo/contrib/pyros/tests/test_config.py | 8 ++--- pyomo/contrib/solver/base.py | 6 ++-- pyomo/contrib/solver/gurobi.py | 6 ++-- pyomo/contrib/solver/persistent.py | 10 +++--- pyomo/contrib/viewer/model_browser.py | 8 ++--- pyomo/core/base/component.py | 2 +- pyomo/core/base/param.py | 35 +++++++++++-------- pyomo/core/expr/calculus/derivatives.py | 2 +- pyomo/core/tests/unit/test_param.py | 10 +++--- pyomo/core/tests/unit/test_visitor.py | 4 +-- pyomo/repn/plugins/ampl/ampl_.py | 8 ++--- pyomo/repn/standard_repn.py | 6 ++-- 26 files changed, 102 insertions(+), 99 deletions(-) diff --git a/pyomo/contrib/appsi/base.py b/pyomo/contrib/appsi/base.py index 1ce24220bfd..e50d5201090 100644 --- a/pyomo/contrib/appsi/base.py +++ b/pyomo/contrib/appsi/base.py @@ -24,7 +24,7 @@ from pyomo.core.base.constraint import GeneralConstraintData, Constraint from pyomo.core.base.sos import _SOSConstraintData, SOSConstraint from pyomo.core.base.var import GeneralVarData, Var -from pyomo.core.base.param import _ParamData, Param +from pyomo.core.base.param import ParamData, Param from pyomo.core.base.block import BlockData, Block from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.collections import ComponentMap @@ -803,7 +803,7 @@ def add_variables(self, variables: List[GeneralVarData]): pass @abc.abstractmethod - def add_params(self, params: List[_ParamData]): + def add_params(self, params: List[ParamData]): pass @abc.abstractmethod @@ -819,7 +819,7 @@ def remove_variables(self, variables: List[GeneralVarData]): pass @abc.abstractmethod - def remove_params(self, params: List[_ParamData]): + def remove_params(self, params: List[ParamData]): pass @abc.abstractmethod @@ -975,10 +975,10 @@ def add_variables(self, variables: List[GeneralVarData]): self._add_variables(variables) @abc.abstractmethod - def _add_params(self, params: List[_ParamData]): + def _add_params(self, params: List[ParamData]): pass - def add_params(self, params: List[_ParamData]): + def add_params(self, params: List[ParamData]): for p in params: self._params[id(p)] = p self._add_params(params) @@ -1198,10 +1198,10 @@ def remove_variables(self, variables: List[GeneralVarData]): del self._vars[v_id] @abc.abstractmethod - def _remove_params(self, params: List[_ParamData]): + def _remove_params(self, params: List[ParamData]): pass - def remove_params(self, params: List[_ParamData]): + def remove_params(self, params: List[ParamData]): self._remove_params(params) for p in params: del self._params[id(p)] diff --git a/pyomo/contrib/appsi/fbbt.py b/pyomo/contrib/appsi/fbbt.py index a360d2bce84..7735318f8ba 100644 --- a/pyomo/contrib/appsi/fbbt.py +++ b/pyomo/contrib/appsi/fbbt.py @@ -19,7 +19,7 @@ from .cmodel import cmodel, cmodel_available from typing import List, Optional from pyomo.core.base.var import GeneralVarData -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData from pyomo.core.base.objective import GeneralObjectiveData, minimize, maximize @@ -143,7 +143,7 @@ def _add_variables(self, variables: List[GeneralVarData]): False, ) - def _add_params(self, params: List[_ParamData]): + def _add_params(self, params: List[ParamData]): cparams = cmodel.create_params(len(params)) for ndx, p in enumerate(params): cp = cparams[ndx] @@ -198,7 +198,7 @@ def _remove_variables(self, variables: List[GeneralVarData]): cvar = self._var_map.pop(id(v)) del self._rvar_map[cvar] - def _remove_params(self, params: List[_ParamData]): + def _remove_params(self, params: List[ParamData]): if self._symbolic_solver_labels: for p in params: self._symbol_map.removeSymbol(p) diff --git a/pyomo/contrib/appsi/solvers/cbc.py b/pyomo/contrib/appsi/solvers/cbc.py index cd5158d905e..d03e6e31c54 100644 --- a/pyomo/contrib/appsi/solvers/cbc.py +++ b/pyomo/contrib/appsi/solvers/cbc.py @@ -29,7 +29,7 @@ from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.timing import HierarchicalTimer from pyomo.common.tee import TeeStream @@ -167,7 +167,7 @@ def set_instance(self, model): def add_variables(self, variables: List[GeneralVarData]): self._writer.add_variables(variables) - def add_params(self, params: List[_ParamData]): + def add_params(self, params: List[ParamData]): self._writer.add_params(params) def add_constraints(self, cons: List[GeneralConstraintData]): @@ -179,7 +179,7 @@ def add_block(self, block: BlockData): def remove_variables(self, variables: List[GeneralVarData]): self._writer.remove_variables(variables) - def remove_params(self, params: List[_ParamData]): + def remove_params(self, params: List[ParamData]): self._writer.remove_params(params) def remove_constraints(self, cons: List[GeneralConstraintData]): diff --git a/pyomo/contrib/appsi/solvers/cplex.py b/pyomo/contrib/appsi/solvers/cplex.py index cdd699105be..55259244d45 100644 --- a/pyomo/contrib/appsi/solvers/cplex.py +++ b/pyomo/contrib/appsi/solvers/cplex.py @@ -25,7 +25,7 @@ from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.timing import HierarchicalTimer import sys @@ -182,7 +182,7 @@ def set_instance(self, model): def add_variables(self, variables: List[GeneralVarData]): self._writer.add_variables(variables) - def add_params(self, params: List[_ParamData]): + def add_params(self, params: List[ParamData]): self._writer.add_params(params) def add_constraints(self, cons: List[GeneralConstraintData]): @@ -194,7 +194,7 @@ def add_block(self, block: BlockData): def remove_variables(self, variables: List[GeneralVarData]): self._writer.remove_variables(variables) - def remove_params(self, params: List[_ParamData]): + def remove_params(self, params: List[ParamData]): self._writer.remove_params(params) def remove_constraints(self, cons: List[GeneralConstraintData]): diff --git a/pyomo/contrib/appsi/solvers/gurobi.py b/pyomo/contrib/appsi/solvers/gurobi.py index 6da59042a80..4392cdf0839 100644 --- a/pyomo/contrib/appsi/solvers/gurobi.py +++ b/pyomo/contrib/appsi/solvers/gurobi.py @@ -26,7 +26,7 @@ from pyomo.core.base.var import Var, GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.expr.numvalue import value, is_constant, is_fixed, native_numeric_types from pyomo.repn import generate_standard_repn from pyomo.core.expr.numeric_expr import NPV_MaxExpression, NPV_MinExpression @@ -489,7 +489,7 @@ def _add_variables(self, variables: List[GeneralVarData]): self._vars_added_since_update.update(variables) self._needs_updated = True - def _add_params(self, params: List[_ParamData]): + def _add_params(self, params: List[ParamData]): pass def _reinit(self): @@ -771,7 +771,7 @@ def _remove_variables(self, variables: List[GeneralVarData]): self._mutable_bounds.pop(v_id, None) self._needs_updated = True - def _remove_params(self, params: List[_ParamData]): + def _remove_params(self, params: List[ParamData]): pass def _update_variables(self, variables: List[GeneralVarData]): diff --git a/pyomo/contrib/appsi/solvers/highs.py b/pyomo/contrib/appsi/solvers/highs.py index ded0092f38b..a6b7c102c91 100644 --- a/pyomo/contrib/appsi/solvers/highs.py +++ b/pyomo/contrib/appsi/solvers/highs.py @@ -23,7 +23,7 @@ from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.expr.numvalue import value, is_constant from pyomo.repn import generate_standard_repn from pyomo.core.expr.numeric_expr import NPV_MaxExpression, NPV_MinExpression @@ -335,7 +335,7 @@ def _add_variables(self, variables: List[GeneralVarData]): len(vtypes), np.array(indices), np.array(vtypes) ) - def _add_params(self, params: List[_ParamData]): + def _add_params(self, params: List[ParamData]): pass def _reinit(self): @@ -515,7 +515,7 @@ def _remove_variables(self, variables: List[GeneralVarData]): self._pyomo_var_to_solver_var_map.clear() self._pyomo_var_to_solver_var_map.update(new_var_map) - def _remove_params(self, params: List[_ParamData]): + def _remove_params(self, params: List[ParamData]): pass def _update_variables(self, variables: List[GeneralVarData]): diff --git a/pyomo/contrib/appsi/solvers/ipopt.py b/pyomo/contrib/appsi/solvers/ipopt.py index 9ccb58095b1..ca75a1b02c8 100644 --- a/pyomo/contrib/appsi/solvers/ipopt.py +++ b/pyomo/contrib/appsi/solvers/ipopt.py @@ -31,7 +31,7 @@ from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.timing import HierarchicalTimer from pyomo.common.tee import TeeStream @@ -231,7 +231,7 @@ def set_instance(self, model): def add_variables(self, variables: List[GeneralVarData]): self._writer.add_variables(variables) - def add_params(self, params: List[_ParamData]): + def add_params(self, params: List[ParamData]): self._writer.add_params(params) def add_constraints(self, cons: List[GeneralConstraintData]): @@ -243,7 +243,7 @@ def add_block(self, block: BlockData): def remove_variables(self, variables: List[GeneralVarData]): self._writer.remove_variables(variables) - def remove_params(self, params: List[_ParamData]): + def remove_params(self, params: List[ParamData]): self._writer.remove_params(params) def remove_constraints(self, cons: List[GeneralConstraintData]): diff --git a/pyomo/contrib/appsi/solvers/wntr.py b/pyomo/contrib/appsi/solvers/wntr.py index 7f633161fe1..8f2650dabb6 100644 --- a/pyomo/contrib/appsi/solvers/wntr.py +++ b/pyomo/contrib/appsi/solvers/wntr.py @@ -41,7 +41,7 @@ from typing import Dict, Optional, List from pyomo.core.base.block import BlockData from pyomo.core.base.var import GeneralVarData -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.common.timing import HierarchicalTimer from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler @@ -270,7 +270,7 @@ def _add_variables(self, variables: List[GeneralVarData]): ) self._needs_updated = True - def _add_params(self, params: List[_ParamData]): + def _add_params(self, params: List[ParamData]): aml = wntr.sim.aml.aml for p in params: pname = self._symbol_map.getSymbol(p, self._labeler) @@ -314,7 +314,7 @@ def _remove_variables(self, variables: List[GeneralVarData]): del self._solver_model._wntr_fixed_var_cons[v_id] self._needs_updated = True - def _remove_params(self, params: List[_ParamData]): + def _remove_params(self, params: List[ParamData]): for p in params: p_id = id(p) solver_param = self._pyomo_param_to_solver_param_map[p_id] diff --git a/pyomo/contrib/appsi/writers/lp_writer.py b/pyomo/contrib/appsi/writers/lp_writer.py index 94af5ba7e93..3a168cdcd91 100644 --- a/pyomo/contrib/appsi/writers/lp_writer.py +++ b/pyomo/contrib/appsi/writers/lp_writer.py @@ -10,7 +10,7 @@ # ___________________________________________________________________________ from typing import List -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData @@ -91,7 +91,7 @@ def _add_variables(self, variables: List[GeneralVarData]): False, ) - def _add_params(self, params: List[_ParamData]): + def _add_params(self, params: List[ParamData]): cparams = cmodel.create_params(len(params)) for ndx, p in enumerate(params): cp = cparams[ndx] @@ -123,7 +123,7 @@ def _remove_variables(self, variables: List[GeneralVarData]): del self._solver_var_to_pyomo_var_map[cvar] self._symbol_map.removeSymbol(v) - def _remove_params(self, params: List[_ParamData]): + def _remove_params(self, params: List[ParamData]): for p in params: del self._pyomo_param_to_solver_param_map[id(p)] self._symbol_map.removeSymbol(p) diff --git a/pyomo/contrib/appsi/writers/nl_writer.py b/pyomo/contrib/appsi/writers/nl_writer.py index b7dab1d5a3e..fced3c5ae10 100644 --- a/pyomo/contrib/appsi/writers/nl_writer.py +++ b/pyomo/contrib/appsi/writers/nl_writer.py @@ -10,7 +10,7 @@ # ___________________________________________________________________________ from typing import List -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData @@ -100,7 +100,7 @@ def _add_variables(self, variables: List[GeneralVarData]): False, ) - def _add_params(self, params: List[_ParamData]): + def _add_params(self, params: List[ParamData]): cparams = cmodel.create_params(len(params)) for ndx, p in enumerate(params): cp = cparams[ndx] @@ -153,7 +153,7 @@ def _remove_variables(self, variables: List[GeneralVarData]): cvar = self._pyomo_var_to_solver_var_map.pop(id(v)) del self._solver_var_to_pyomo_var_map[cvar] - def _remove_params(self, params: List[_ParamData]): + def _remove_params(self, params: List[ParamData]): if self.config.symbolic_solver_labels: for p in params: self._symbol_map.removeSymbol(p) diff --git a/pyomo/contrib/cp/repn/docplex_writer.py b/pyomo/contrib/cp/repn/docplex_writer.py index eb50a543160..75095755895 100644 --- a/pyomo/contrib/cp/repn/docplex_writer.py +++ b/pyomo/contrib/cp/repn/docplex_writer.py @@ -64,7 +64,7 @@ IndexedBooleanVar, ) from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData -from pyomo.core.base.param import IndexedParam, ScalarParam, _ParamData +from pyomo.core.base.param import IndexedParam, ScalarParam, ParamData from pyomo.core.base.var import ScalarVar, GeneralVarData, IndexedVar import pyomo.core.expr as EXPR from pyomo.core.expr.visitor import StreamBasedExpressionVisitor, identify_variables @@ -970,7 +970,7 @@ class LogicalToDoCplex(StreamBasedExpressionVisitor): ScalarExpression: _before_named_expression, IndexedParam: _before_indexed_param, # Because of indirection ScalarParam: _before_param, - _ParamData: _before_param, + ParamData: _before_param, } def __init__(self, cpx_model, symbolic_solver_labels=False): diff --git a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py index 26b63d020a5..a228b1561dd 100644 --- a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py +++ b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py @@ -28,7 +28,7 @@ ) import pyomo.core.base.boolean_var as BV from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData -from pyomo.core.base.param import ScalarParam, _ParamData +from pyomo.core.base.param import ScalarParam, ParamData from pyomo.core.base.var import ScalarVar, GeneralVarData from pyomo.gdp.disjunct import AutoLinkedBooleanVar, Disjunct, Disjunction @@ -211,7 +211,7 @@ def _dispatch_atmost(visitor, node, *args): _before_child_dispatcher[BV.ScalarBooleanVar] = _dispatch_boolean_var _before_child_dispatcher[BV.GeneralBooleanVarData] = _dispatch_boolean_var _before_child_dispatcher[AutoLinkedBooleanVar] = _dispatch_boolean_var -_before_child_dispatcher[_ParamData] = _dispatch_param +_before_child_dispatcher[ParamData] = _dispatch_param _before_child_dispatcher[ScalarParam] = _dispatch_param # for the moment, these are all just so we can get good error messages when we # don't handle them: diff --git a/pyomo/contrib/latex_printer/latex_printer.py b/pyomo/contrib/latex_printer/latex_printer.py index efcd3016dbf..dec058bb5ba 100644 --- a/pyomo/contrib/latex_printer/latex_printer.py +++ b/pyomo/contrib/latex_printer/latex_printer.py @@ -48,7 +48,7 @@ templatize_rule, ) from pyomo.core.base.var import ScalarVar, GeneralVarData, IndexedVar -from pyomo.core.base.param import _ParamData, ScalarParam, IndexedParam +from pyomo.core.base.param import ParamData, ScalarParam, IndexedParam from pyomo.core.base.set import _SetData, SetOperator from pyomo.core.base.constraint import ScalarConstraint, IndexedConstraint from pyomo.common.collections.component_map import ComponentMap @@ -417,7 +417,7 @@ def __init__(self): Numeric_GetItemExpression: handle_numericGetItemExpression_node, TemplateSumExpression: handle_templateSumExpression_node, ScalarParam: handle_param_node, - _ParamData: handle_param_node, + ParamData: handle_param_node, IndexedParam: handle_param_node, NPV_Numeric_GetItemExpression: handle_numericGetItemExpression_node, IndexedBlock: handle_indexedBlock_node, @@ -717,10 +717,8 @@ def latex_printer( variableList.append(v) parameterList = [] - for p in identify_components( - temp_comp, [ScalarParam, _ParamData, IndexedParam] - ): - if isinstance(p, _ParamData): + for p in identify_components(temp_comp, [ScalarParam, ParamData, IndexedParam]): + if isinstance(p, ParamData): p_write = p.parent_component() if p_write not in ComponentSet(parameterList): parameterList.append(p_write) @@ -1280,7 +1278,7 @@ def get_index_names(st, lcm): if ky not in existing_components: overwrite_value = overwrite_value.replace('_', '\\_') rep_dict[variableMap[ky]] = overwrite_value - elif isinstance(ky, (pyo.Param, _ParamData)): + elif isinstance(ky, (pyo.Param, ParamData)): overwrite_value = latex_component_map[ky] if ky not in existing_components: overwrite_value = overwrite_value.replace('_', '\\_') diff --git a/pyomo/contrib/pyros/config.py b/pyomo/contrib/pyros/config.py index bc2bfd591e6..e60b474d037 100644 --- a/pyomo/contrib/pyros/config.py +++ b/pyomo/contrib/pyros/config.py @@ -17,7 +17,7 @@ ) from pyomo.common.errors import ApplicationError, PyomoException from pyomo.core.base import Var, _VarData -from pyomo.core.base.param import Param, _ParamData +from pyomo.core.base.param import Param, ParamData from pyomo.opt import SolverFactory from pyomo.contrib.pyros.util import ObjectiveType, setup_pyros_logger from pyomo.contrib.pyros.uncertainty_sets import UncertaintySet @@ -62,7 +62,7 @@ def mutable_param_validator(param_obj): Parameters ---------- - param_obj : Param or _ParamData + param_obj : Param or ParamData Param-like object of interest. Raises @@ -98,7 +98,7 @@ class InputDataStandardizer(object): Pyomo component type, such as Component, Var or Param. cdatatype : type Corresponding Pyomo component data type, such as - _ComponentData, _VarData, or _ParamData. + _ComponentData, _VarData, or ParamData. ctype_validator : callable, optional Validator function for objects of type `ctype`. cdatatype_validator : callable, optional @@ -531,7 +531,7 @@ def pyros_config(): default=[], domain=InputDataStandardizer( ctype=Param, - cdatatype=_ParamData, + cdatatype=ParamData, ctype_validator=mutable_param_validator, allow_repeats=False, ), diff --git a/pyomo/contrib/pyros/tests/test_config.py b/pyomo/contrib/pyros/tests/test_config.py index 0f52d04135d..cd635e795fc 100644 --- a/pyomo/contrib/pyros/tests/test_config.py +++ b/pyomo/contrib/pyros/tests/test_config.py @@ -8,7 +8,7 @@ from pyomo.core.base import ConcreteModel, Var, _VarData from pyomo.common.log import LoggingIntercept from pyomo.common.errors import ApplicationError -from pyomo.core.base.param import Param, _ParamData +from pyomo.core.base.param import Param, ParamData from pyomo.contrib.pyros.config import ( InputDataStandardizer, mutable_param_validator, @@ -201,7 +201,7 @@ def test_standardizer_invalid_uninitialized_params(self): uninitialized entries passed. """ standardizer_func = InputDataStandardizer( - ctype=Param, cdatatype=_ParamData, ctype_validator=mutable_param_validator + ctype=Param, cdatatype=ParamData, ctype_validator=mutable_param_validator ) mdl = ConcreteModel() @@ -217,7 +217,7 @@ def test_standardizer_invalid_immutable_params(self): Param object(s) passed. """ standardizer_func = InputDataStandardizer( - ctype=Param, cdatatype=_ParamData, ctype_validator=mutable_param_validator + ctype=Param, cdatatype=ParamData, ctype_validator=mutable_param_validator ) mdl = ConcreteModel() @@ -237,7 +237,7 @@ def test_standardizer_valid_mutable_params(self): mdl.p2 = Param(["a", "b"], initialize=1, mutable=True) standardizer_func = InputDataStandardizer( - ctype=Param, cdatatype=_ParamData, ctype_validator=mutable_param_validator + ctype=Param, cdatatype=ParamData, ctype_validator=mutable_param_validator ) standardizer_input = [mdl.p1[0], mdl.p2] diff --git a/pyomo/contrib/solver/base.py b/pyomo/contrib/solver/base.py index a935a950819..1b22c17cf48 100644 --- a/pyomo/contrib/solver/base.py +++ b/pyomo/contrib/solver/base.py @@ -16,7 +16,7 @@ from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.var import GeneralVarData -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.base.block import BlockData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.config import document_kwargs_from_configdict, ConfigValue @@ -288,7 +288,7 @@ def add_variables(self, variables: List[GeneralVarData]): """ @abc.abstractmethod - def add_parameters(self, params: List[_ParamData]): + def add_parameters(self, params: List[ParamData]): """ Add parameters to the model """ @@ -312,7 +312,7 @@ def remove_variables(self, variables: List[GeneralVarData]): """ @abc.abstractmethod - def remove_parameters(self, params: List[_ParamData]): + def remove_parameters(self, params: List[ParamData]): """ Remove parameters from the model """ diff --git a/pyomo/contrib/solver/gurobi.py b/pyomo/contrib/solver/gurobi.py index 353798133db..107de15e625 100644 --- a/pyomo/contrib/solver/gurobi.py +++ b/pyomo/contrib/solver/gurobi.py @@ -25,7 +25,7 @@ from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import _SOSConstraintData -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.expr.numvalue import value, is_constant, is_fixed, native_numeric_types from pyomo.repn import generate_standard_repn from pyomo.core.expr.numeric_expr import NPV_MaxExpression, NPV_MinExpression @@ -469,7 +469,7 @@ def _add_variables(self, variables: List[GeneralVarData]): self._vars_added_since_update.update(variables) self._needs_updated = True - def _add_parameters(self, params: List[_ParamData]): + def _add_parameters(self, params: List[ParamData]): pass def _reinit(self): @@ -747,7 +747,7 @@ def _remove_variables(self, variables: List[GeneralVarData]): self._mutable_bounds.pop(v_id, None) self._needs_updated = True - def _remove_parameters(self, params: List[_ParamData]): + def _remove_parameters(self, params: List[ParamData]): pass def _update_variables(self, variables: List[GeneralVarData]): diff --git a/pyomo/contrib/solver/persistent.py b/pyomo/contrib/solver/persistent.py index aeacc9f87c4..558b8cbf314 100644 --- a/pyomo/contrib/solver/persistent.py +++ b/pyomo/contrib/solver/persistent.py @@ -15,7 +15,7 @@ from pyomo.core.base.constraint import GeneralConstraintData, Constraint from pyomo.core.base.sos import _SOSConstraintData, SOSConstraint from pyomo.core.base.var import GeneralVarData -from pyomo.core.base.param import _ParamData, Param +from pyomo.core.base.param import ParamData, Param from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.collections import ComponentMap from pyomo.common.timing import HierarchicalTimer @@ -75,10 +75,10 @@ def add_variables(self, variables: List[GeneralVarData]): self._add_variables(variables) @abc.abstractmethod - def _add_parameters(self, params: List[_ParamData]): + def _add_parameters(self, params: List[ParamData]): pass - def add_parameters(self, params: List[_ParamData]): + def add_parameters(self, params: List[ParamData]): for p in params: self._params[id(p)] = p self._add_parameters(params) @@ -274,10 +274,10 @@ def remove_variables(self, variables: List[GeneralVarData]): del self._vars[v_id] @abc.abstractmethod - def _remove_parameters(self, params: List[_ParamData]): + def _remove_parameters(self, params: List[ParamData]): pass - def remove_parameters(self, params: List[_ParamData]): + def remove_parameters(self, params: List[ParamData]): self._remove_parameters(params) for p in params: del self._params[id(p)] diff --git a/pyomo/contrib/viewer/model_browser.py b/pyomo/contrib/viewer/model_browser.py index 5887a577ba0..91dc946c55d 100644 --- a/pyomo/contrib/viewer/model_browser.py +++ b/pyomo/contrib/viewer/model_browser.py @@ -33,7 +33,7 @@ import pyomo.contrib.viewer.qt as myqt from pyomo.contrib.viewer.report import value_no_exception, get_residual -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.environ import ( Block, BooleanVar, @@ -243,7 +243,7 @@ def _get_expr_callback(self): return None def _get_value_callback(self): - if isinstance(self.data, _ParamData): + if isinstance(self.data, ParamData): v = value_no_exception(self.data, div0="divide_by_0") # Check the param value for numpy float and int, sometimes numpy # values can sneak in especially if you set parameters from data @@ -295,7 +295,7 @@ def _get_residual_callback(self): def _get_units_callback(self): if isinstance(self.data, (Var, Var._ComponentDataClass)): return str(units.get_units(self.data)) - if isinstance(self.data, (Param, _ParamData)): + if isinstance(self.data, (Param, ParamData)): return str(units.get_units(self.data)) return self._cache_units @@ -320,7 +320,7 @@ def _set_value_callback(self, val): o.value = val except: return - elif isinstance(self.data, _ParamData): + elif isinstance(self.data, ParamData): if not self.data.parent_component().mutable: return try: diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 341cd1506ff..33b2f5c686c 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -805,7 +805,7 @@ class ComponentData(_ComponentBase): # classes: BooleanVarData, ConnectorData, ConstraintData, # GeneralExpressionData, LogicalConstraintData, # GeneralLogicalConstraintData, GeneralObjectiveData, - # _ParamData,GeneralVarData, GeneralBooleanVarData, DisjunctionData, + # ParamData,GeneralVarData, GeneralBooleanVarData, DisjunctionData, # ArcData, _PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those # constructors as well! diff --git a/pyomo/core/base/param.py b/pyomo/core/base/param.py index 5fcaf92b25a..9af6a37de45 100644 --- a/pyomo/core/base/param.py +++ b/pyomo/core/base/param.py @@ -118,7 +118,7 @@ def _parent(self, val): pass -class _ParamData(ComponentData, NumericValue): +class ParamData(ComponentData, NumericValue): """ This class defines the data for a mutable parameter. @@ -252,6 +252,11 @@ def _compute_polynomial_degree(self, result): return 0 +class _ParamData(metaclass=RenamedClass): + __renamed__new_class__ = ParamData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register( "Parameter data that is used to define a model instance." ) @@ -285,7 +290,7 @@ class Param(IndexedComponent, IndexedComponent_NDArrayMixin): """ DefaultMutable = False - _ComponentDataClass = _ParamData + _ComponentDataClass = ParamData class NoValue(object): """A dummy type that is pickle-safe that we can use as the default @@ -523,14 +528,14 @@ def store_values(self, new_values, check=True): # instead of incurring the penalty of checking. for index, new_value in new_values.items(): if index not in self._data: - self._data[index] = _ParamData(self) + self._data[index] = ParamData(self) self._data[index]._value = new_value else: # For scalars, we will choose an approach based on # how "dense" the Param is if not self._data: # empty for index in self._index_set: - p = self._data[index] = _ParamData(self) + p = self._data[index] = ParamData(self) p._value = new_values elif len(self._data) == len(self._index_set): for index in self._index_set: @@ -538,7 +543,7 @@ def store_values(self, new_values, check=True): else: for index in self._index_set: if index not in self._data: - self._data[index] = _ParamData(self) + self._data[index] = ParamData(self) self._data[index]._value = new_values else: # @@ -601,9 +606,9 @@ def _getitem_when_not_present(self, index): # a default value, as long as *solving* a model without # reasonable values produces an informative error. if self._mutable: - # Note: _ParamData defaults to Param.NoValue + # Note: ParamData defaults to Param.NoValue if self.is_indexed(): - ans = self._data[index] = _ParamData(self) + ans = self._data[index] = ParamData(self) else: ans = self._data[index] = self ans._index = index @@ -698,8 +703,8 @@ def _setitem_impl(self, index, obj, value): return obj else: old_value, self._data[index] = self._data[index], value - # Because we do not have a _ParamData, we cannot rely on the - # validation that occurs in _ParamData.set_value() + # Because we do not have a ParamData, we cannot rely on the + # validation that occurs in ParamData.set_value() try: self._validate_value(index, value) return value @@ -736,14 +741,14 @@ def _setitem_when_not_present(self, index, value, _check_domain=True): self._index = UnindexedComponent_index return self elif self._mutable: - obj = self._data[index] = _ParamData(self) + obj = self._data[index] = ParamData(self) obj.set_value(value, index) obj._index = index return obj else: self._data[index] = value - # Because we do not have a _ParamData, we cannot rely on the - # validation that occurs in _ParamData.set_value() + # Because we do not have a ParamData, we cannot rely on the + # validation that occurs in ParamData.set_value() self._validate_value(index, value, _check_domain) return value except: @@ -901,9 +906,9 @@ def _pprint(self): return (headers, self.sparse_iteritems(), ("Value",), dataGen) -class ScalarParam(_ParamData, Param): +class ScalarParam(ParamData, Param): def __init__(self, *args, **kwds): - _ParamData.__init__(self, component=self) + ParamData.__init__(self, component=self) Param.__init__(self, *args, **kwds) self._index = UnindexedComponent_index @@ -996,7 +1001,7 @@ def _create_objects_for_deepcopy(self, memo, component_list): # between potentially variable GetItemExpression objects and # "constant" GetItemExpression objects. That will need to wait for # the expression rework [JDS; Nov 22]. - def __getitem__(self, args) -> _ParamData: + def __getitem__(self, args) -> ParamData: try: return super().__getitem__(args) except: diff --git a/pyomo/core/expr/calculus/derivatives.py b/pyomo/core/expr/calculus/derivatives.py index cd23cb16b2c..5df1fd3c65e 100644 --- a/pyomo/core/expr/calculus/derivatives.py +++ b/pyomo/core/expr/calculus/derivatives.py @@ -42,7 +42,7 @@ def differentiate(expr, wrt=None, wrt_list=None, mode=Modes.reverse_numeric): wrt: pyomo.core.base.var.GeneralVarData If specified, this function will return the derivative with respect to wrt. wrt is normally a GeneralVarData, but could - also be a _ParamData. wrt and wrt_list cannot both be specified. + also be a ParamData. wrt and wrt_list cannot both be specified. wrt_list: list of pyomo.core.base.var.GeneralVarData If specified, this function will return the derivative with respect to each element in wrt_list. A list will be returned diff --git a/pyomo/core/tests/unit/test_param.py b/pyomo/core/tests/unit/test_param.py index 9bc0c4b2ad2..b39272879f6 100644 --- a/pyomo/core/tests/unit/test_param.py +++ b/pyomo/core/tests/unit/test_param.py @@ -65,7 +65,7 @@ from pyomo.common.errors import PyomoException from pyomo.common.log import LoggingIntercept from pyomo.common.tempfiles import TempfileManager -from pyomo.core.base.param import _ParamData +from pyomo.core.base.param import ParamData from pyomo.core.base.set import _SetData from pyomo.core.base.units_container import units, pint_available, UnitsError @@ -181,7 +181,7 @@ def test_setitem_preexisting(self): idx = sorted(keys)[0] self.assertEqual(value(self.instance.A[idx]), self.data[idx]) if self.instance.A.mutable: - self.assertTrue(isinstance(self.instance.A[idx], _ParamData)) + self.assertTrue(isinstance(self.instance.A[idx], ParamData)) else: self.assertEqual(type(self.instance.A[idx]), float) @@ -190,7 +190,7 @@ def test_setitem_preexisting(self): if not self.instance.A.mutable: self.fail("Expected setitem[%s] to fail for immutable Params" % (idx,)) self.assertEqual(value(self.instance.A[idx]), 4.3) - self.assertTrue(isinstance(self.instance.A[idx], _ParamData)) + self.assertTrue(isinstance(self.instance.A[idx], ParamData)) except TypeError: # immutable Params should raise a TypeError exception if self.instance.A.mutable: @@ -249,7 +249,7 @@ def test_setitem_default_override(self): self.assertEqual(value(self.instance.A[idx]), self.instance.A._default_val) if self.instance.A.mutable: - self.assertIsInstance(self.instance.A[idx], _ParamData) + self.assertIsInstance(self.instance.A[idx], ParamData) else: self.assertEqual( type(self.instance.A[idx]), type(value(self.instance.A._default_val)) @@ -260,7 +260,7 @@ def test_setitem_default_override(self): if not self.instance.A.mutable: self.fail("Expected setitem[%s] to fail for immutable Params" % (idx,)) self.assertEqual(self.instance.A[idx].value, 4.3) - self.assertIsInstance(self.instance.A[idx], _ParamData) + self.assertIsInstance(self.instance.A[idx], ParamData) except TypeError: # immutable Params should raise a TypeError exception if self.instance.A.mutable: diff --git a/pyomo/core/tests/unit/test_visitor.py b/pyomo/core/tests/unit/test_visitor.py index 12fb98d1d19..ac61a3a24c7 100644 --- a/pyomo/core/tests/unit/test_visitor.py +++ b/pyomo/core/tests/unit/test_visitor.py @@ -72,7 +72,7 @@ RECURSION_LIMIT, get_stack_depth, ) -from pyomo.core.base.param import _ParamData, ScalarParam +from pyomo.core.base.param import ParamData, ScalarParam from pyomo.core.expr.template_expr import IndexTemplate from pyomo.common.collections import ComponentSet from pyomo.common.errors import TemplateExpressionError @@ -685,7 +685,7 @@ def __init__(self, model): self.model = model def visiting_potential_leaf(self, node): - if node.__class__ in (_ParamData, ScalarParam): + if node.__class__ in (ParamData, ScalarParam): if id(node) in self.substitute: return True, self.substitute[id(node)] self.substitute[id(node)] = 2 * self.model.w.add() diff --git a/pyomo/repn/plugins/ampl/ampl_.py b/pyomo/repn/plugins/ampl/ampl_.py index c6357cbecd9..840bee2166c 100644 --- a/pyomo/repn/plugins/ampl/ampl_.py +++ b/pyomo/repn/plugins/ampl/ampl_.py @@ -171,8 +171,8 @@ def _build_op_template(): _op_template[var._VarData] = "v%d{C}\n" _op_comment[var._VarData] = "\t#%s" - _op_template[param._ParamData] = "n%r{C}\n" - _op_comment[param._ParamData] = "" + _op_template[param.ParamData] = "n%r{C}\n" + _op_comment[param.ParamData] = "" _op_template[NumericConstant] = "n%r{C}\n" _op_comment[NumericConstant] = "" @@ -749,8 +749,8 @@ def _print_nonlinear_terms_NL(self, exp): ) ) - elif isinstance(exp, param._ParamData): - OUTPUT.write(self._op_string[param._ParamData] % (value(exp))) + elif isinstance(exp, param.ParamData): + OUTPUT.write(self._op_string[param.ParamData] % (value(exp))) elif isinstance(exp, NumericConstant) or exp.is_fixed(): OUTPUT.write(self._op_string[NumericConstant] % (value(exp))) diff --git a/pyomo/repn/standard_repn.py b/pyomo/repn/standard_repn.py index 907b4a2b115..5786d078385 100644 --- a/pyomo/repn/standard_repn.py +++ b/pyomo/repn/standard_repn.py @@ -23,7 +23,7 @@ from pyomo.core.base import ExpressionData, Expression from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.var import ScalarVar, Var, GeneralVarData, value -from pyomo.core.base.param import ScalarParam, _ParamData +from pyomo.core.base.param import ScalarParam, ParamData from pyomo.core.kernel.expression import expression, noclone from pyomo.core.kernel.variable import IVariable, variable from pyomo.core.kernel.objective import objective @@ -1138,7 +1138,7 @@ def _collect_external_fn(exp, multiplier, idMap, compute_values, verbose, quadra EXPR.ExternalFunctionExpression: _collect_external_fn, # ConnectorData : _collect_linear_connector, # ScalarConnector : _collect_linear_connector, - _ParamData: _collect_const, + ParamData: _collect_const, ScalarParam: _collect_const, # param.Param : _collect_linear_const, # parameter : _collect_linear_const, @@ -1538,7 +1538,7 @@ def _linear_collect_pow(exp, multiplier, idMap, compute_values, verbose, coef): ##EXPR.LinearSumExpression : _collect_linear_sum, ##ConnectorData : _collect_linear_connector, ##ScalarConnector : _collect_linear_connector, - ##param._ParamData : _collect_linear_const, + ##param.ParamData : _collect_linear_const, ##param.ScalarParam : _collect_linear_const, ##param.Param : _collect_linear_const, ##parameter : _collect_linear_const, From 8c968e3e976bc8ea8c551a7c48d275d623e04559 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:51:57 -0600 Subject: [PATCH 24/83] Renamed _PiecewiseData -> PiecewiseData --- pyomo/core/base/piecewise.py | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/pyomo/core/base/piecewise.py b/pyomo/core/base/piecewise.py index b15def13ccb..43f8ddbfef5 100644 --- a/pyomo/core/base/piecewise.py +++ b/pyomo/core/base/piecewise.py @@ -214,7 +214,7 @@ def _characterize_function(name, tol, f_rule, model, points, *index): return 0, values, False -class _PiecewiseData(BlockData): +class PiecewiseData(BlockData): """ This class defines the base class for all linearization and piecewise constraint generators.. @@ -272,6 +272,11 @@ def __call__(self, x): ) +class _PiecewiseData(metaclass=RenamedClass): + __renamed__new_class__ = PiecewiseData + __renamed__version__ = '6.7.2.dev0' + + class _SimpleSinglePiecewise(object): """ Called when the piecewise points list has only two points @@ -1125,7 +1130,7 @@ def f(model,j,x): not be modified. """ - _ComponentDataClass = _PiecewiseData + _ComponentDataClass = PiecewiseData def __new__(cls, *args, **kwds): if cls != Piecewise: @@ -1541,7 +1546,7 @@ def add(self, index, _is_indexed=None): raise ValueError(msg % (self.name, index, self._pw_rep)) if _is_indexed: - comp = _PiecewiseData(self) + comp = PiecewiseData(self) else: comp = self self._data[index] = comp @@ -1551,9 +1556,9 @@ def add(self, index, _is_indexed=None): comp.build_constraints(func, _self_xvar, _self_yvar) -class SimplePiecewise(_PiecewiseData, Piecewise): +class SimplePiecewise(PiecewiseData, Piecewise): def __init__(self, *args, **kwds): - _PiecewiseData.__init__(self, self) + PiecewiseData.__init__(self, self) Piecewise.__init__(self, *args, **kwds) From 590e21fad08496e01fc6611fe506867b2ae6217d Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:52:11 -0600 Subject: [PATCH 25/83] Renamed _PortData -> PortData --- pyomo/core/base/component.py | 2 +- pyomo/network/port.py | 15 ++++++++++----- 2 files changed, 11 insertions(+), 6 deletions(-) diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 33b2f5c686c..7a4b7e40aab 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -806,7 +806,7 @@ class ComponentData(_ComponentBase): # GeneralExpressionData, LogicalConstraintData, # GeneralLogicalConstraintData, GeneralObjectiveData, # ParamData,GeneralVarData, GeneralBooleanVarData, DisjunctionData, - # ArcData, _PortData, _LinearConstraintData, and + # ArcData, PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those # constructors as well! def __init__(self, component): diff --git a/pyomo/network/port.py b/pyomo/network/port.py index 26822d4fee9..ee5c915d8db 100644 --- a/pyomo/network/port.py +++ b/pyomo/network/port.py @@ -36,7 +36,7 @@ logger = logging.getLogger('pyomo.network') -class _PortData(ComponentData): +class PortData(ComponentData): """ This class defines the data for a single Port @@ -285,6 +285,11 @@ def get_split_fraction(self, arc): return res +class _PortData(metaclass=RenamedClass): + __renamed__new_class__ = PortData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register( "A bundle of variables that can be connected to other ports." ) @@ -339,7 +344,7 @@ def __init__(self, *args, **kwd): # IndexedComponent that support implicit definition def _getitem_when_not_present(self, idx): """Returns the default component data value.""" - tmp = self._data[idx] = _PortData(component=self) + tmp = self._data[idx] = PortData(component=self) tmp._index = idx return tmp @@ -357,7 +362,7 @@ def construct(self, data=None): for _set in self._anonymous_sets: _set.construct() - # Construct _PortData objects for all index values + # Construct PortData objects for all index values if self.is_indexed(): self._initialize_members(self._index_set) else: @@ -763,9 +768,9 @@ def _create_evar(member, name, eblock, index_set): return evar -class ScalarPort(Port, _PortData): +class ScalarPort(Port, PortData): def __init__(self, *args, **kwd): - _PortData.__init__(self, component=self) + PortData.__init__(self, component=self) Port.__init__(self, *args, **kwd) self._index = UnindexedComponent_index From 199ee006d445859f7d796f528a8b326cf883f3f6 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:55:57 -0600 Subject: [PATCH 26/83] Renamed _SetData -> SetData --- pyomo/contrib/latex_printer/latex_printer.py | 4 +- pyomo/core/base/set.py | 51 +++++++++++--------- pyomo/core/base/sets.py | 4 +- pyomo/core/tests/unit/test_param.py | 4 +- pyomo/core/tests/unit/test_set.py | 18 +++---- 5 files changed, 43 insertions(+), 38 deletions(-) diff --git a/pyomo/contrib/latex_printer/latex_printer.py b/pyomo/contrib/latex_printer/latex_printer.py index dec058bb5ba..28d1ca52943 100644 --- a/pyomo/contrib/latex_printer/latex_printer.py +++ b/pyomo/contrib/latex_printer/latex_printer.py @@ -49,7 +49,7 @@ ) from pyomo.core.base.var import ScalarVar, GeneralVarData, IndexedVar from pyomo.core.base.param import ParamData, ScalarParam, IndexedParam -from pyomo.core.base.set import _SetData, SetOperator +from pyomo.core.base.set import SetData, SetOperator from pyomo.core.base.constraint import ScalarConstraint, IndexedConstraint from pyomo.common.collections.component_map import ComponentMap from pyomo.common.collections.component_set import ComponentSet @@ -1283,7 +1283,7 @@ def get_index_names(st, lcm): if ky not in existing_components: overwrite_value = overwrite_value.replace('_', '\\_') rep_dict[parameterMap[ky]] = overwrite_value - elif isinstance(ky, _SetData): + elif isinstance(ky, SetData): # already handled pass elif isinstance(ky, (float, int)): diff --git a/pyomo/core/base/set.py b/pyomo/core/base/set.py index c7a7edc8e4b..3280f512e83 100644 --- a/pyomo/core/base/set.py +++ b/pyomo/core/base/set.py @@ -87,7 +87,7 @@ 0. `class _SetDataBase(ComponentData)` *(pure virtual interface)* -1. `class _SetData(_SetDataBase)` +1. `class SetData(_SetDataBase)` *(base class for all AML Sets)* 2. `class _FiniteSetMixin(object)` @@ -102,7 +102,7 @@ bounded continuous ranges as well as unbounded discrete ranges). As there are an infinite number of values, iteration is *not* supported. The base class also implements all Python set operations. -Note that `_SetData` does *not* implement `len()`, as Python requires +Note that `SetData` does *not* implement `len()`, as Python requires `len()` to return a positive integer. Finite sets add iteration and support for `len()`. In addition, they @@ -520,7 +520,7 @@ class _SetDataBase(ComponentData): __slots__ = () -class _SetData(_SetDataBase): +class SetData(_SetDataBase): """The base for all Pyomo AML objects that can be used as a component indexing set. @@ -534,13 +534,13 @@ def __contains__(self, value): ans = self.get(value, _NotFound) except TypeError: # In Python 3.x, Sets are unhashable - if isinstance(value, _SetData): + if isinstance(value, SetData): ans = _NotFound else: raise if ans is _NotFound: - if isinstance(value, _SetData): + if isinstance(value, SetData): deprecation_warning( "Testing for set subsets with 'a in b' is deprecated. " "Use 'a.issubset(b)'.", @@ -1188,6 +1188,11 @@ def __gt__(self, other): return self >= other and not self == other +class _SetData(metaclass=RenamedClass): + __renamed__new_class__ = SetData + __renamed__version__ = '6.7.2.dev0' + + class _FiniteSetMixin(object): __slots__ = () @@ -1294,13 +1299,13 @@ def ranges(self): yield NonNumericRange(i) -class FiniteSetData(_FiniteSetMixin, _SetData): +class FiniteSetData(_FiniteSetMixin, SetData): """A general unordered iterable Set""" __slots__ = ('_values', '_domain', '_validate', '_filter', '_dimen') def __init__(self, component): - _SetData.__init__(self, component=component) + SetData.__init__(self, component=component) # Derived classes (like OrderedSetData) may want to change the # storage if not hasattr(self, '_values'): @@ -1986,7 +1991,7 @@ class SortedOrder(object): _UnorderedInitializers = {set} @overload - def __new__(cls: Type[Set], *args, **kwds) -> Union[_SetData, IndexedSet]: ... + def __new__(cls: Type[Set], *args, **kwds) -> Union[SetData, IndexedSet]: ... @overload def __new__(cls: Type[OrderedScalarSet], *args, **kwds) -> OrderedScalarSet: ... @@ -2193,7 +2198,7 @@ def _getitem_when_not_present(self, index): """Returns the default component data value.""" # Because we allow sets within an IndexedSet to have different # dimen, we have moved the tuplization logic from PyomoModel - # into Set (because we cannot know the dimen of a _SetData until + # into Set (because we cannot know the dimen of a SetData until # we are actually constructing that index). This also means # that we need to potentially communicate the dimen to the # (wrapped) value initializer. So, we will get the dimen first, @@ -2353,7 +2358,7 @@ def _pprint(self): # else: # return '{' + str(ans)[1:-1] + "}" - # TBD: In the current design, we force all _SetData within an + # TBD: In the current design, we force all SetData within an # indexed Set to have the same isordered value, so we will only # print it once in the header. Is this a good design? try: @@ -2398,7 +2403,7 @@ def data(self): return {k: v.data() for k, v in self.items()} @overload - def __getitem__(self, index) -> _SetData: ... + def __getitem__(self, index) -> SetData: ... __getitem__ = IndexedComponent.__getitem__ # type: ignore @@ -2479,14 +2484,14 @@ class AbstractSortedSimpleSet(metaclass=RenamedClass): ############################################################################ -class SetOf(_SetData, Component): +class SetOf(SetData, Component): """""" def __new__(cls, *args, **kwds): if cls is not SetOf: return super(SetOf, cls).__new__(cls) (reference,) = args - if isinstance(reference, (_SetData, GlobalSetBase)): + if isinstance(reference, (SetData, GlobalSetBase)): if reference.isfinite(): if reference.isordered(): return super(SetOf, cls).__new__(OrderedSetOf) @@ -2500,7 +2505,7 @@ def __new__(cls, *args, **kwds): return super(SetOf, cls).__new__(FiniteSetOf) def __init__(self, reference, **kwds): - _SetData.__init__(self, component=self) + SetData.__init__(self, component=self) kwds.setdefault('ctype', SetOf) Component.__init__(self, **kwds) self._ref = reference @@ -2523,7 +2528,7 @@ def construct(self, data=None): @property def dimen(self): - if isinstance(self._ref, _SetData): + if isinstance(self._ref, SetData): return self._ref.dimen _iter = iter(self) try: @@ -2618,7 +2623,7 @@ def ord(self, item): ############################################################################ -class InfiniteRangeSetData(_SetData): +class InfiniteRangeSetData(SetData): """Data class for a infinite set. This Set implements an interface to an *infinite set* defined by one @@ -2630,7 +2635,7 @@ class InfiniteRangeSetData(_SetData): __slots__ = ('_ranges',) def __init__(self, component): - _SetData.__init__(self, component=component) + SetData.__init__(self, component=component) self._ranges = None def get(self, value, default=None): @@ -3298,11 +3303,11 @@ class AbstractFiniteSimpleRangeSet(metaclass=RenamedClass): ############################################################################ -class SetOperator(_SetData, Set): +class SetOperator(SetData, Set): __slots__ = ('_sets',) def __init__(self, *args, **kwds): - _SetData.__init__(self, component=self) + SetData.__init__(self, component=self) Set.__init__(self, **kwds) self._sets, _anonymous = zip(*(process_setarg(_set) for _set in args)) _anonymous = tuple(filter(None, _anonymous)) @@ -4242,9 +4247,9 @@ def ord(self, item): ############################################################################ -class _AnySet(_SetData, Set): +class _AnySet(SetData, Set): def __init__(self, **kwds): - _SetData.__init__(self, component=self) + SetData.__init__(self, component=self) # There is a chicken-and-egg game here: the SetInitializer uses # Any as part of the processing of the domain/within/bounds # domain restrictions. However, Any has not been declared when @@ -4298,9 +4303,9 @@ def get(self, val, default=None): return super(_AnyWithNoneSet, self).get(val, default) -class _EmptySet(_FiniteSetMixin, _SetData, Set): +class _EmptySet(_FiniteSetMixin, SetData, Set): def __init__(self, **kwds): - _SetData.__init__(self, component=self) + SetData.__init__(self, component=self) Set.__init__(self, **kwds) self.construct() diff --git a/pyomo/core/base/sets.py b/pyomo/core/base/sets.py index ca693cf7d8b..3ebdc6875d1 100644 --- a/pyomo/core/base/sets.py +++ b/pyomo/core/base/sets.py @@ -17,8 +17,8 @@ process_setarg, set_options, simple_set_rule, - _SetDataBase, - _SetData, + SetDataBase, + SetData, Set, SetOf, IndexedSet, diff --git a/pyomo/core/tests/unit/test_param.py b/pyomo/core/tests/unit/test_param.py index b39272879f6..f22674b6bf7 100644 --- a/pyomo/core/tests/unit/test_param.py +++ b/pyomo/core/tests/unit/test_param.py @@ -66,7 +66,7 @@ from pyomo.common.log import LoggingIntercept from pyomo.common.tempfiles import TempfileManager from pyomo.core.base.param import ParamData -from pyomo.core.base.set import _SetData +from pyomo.core.base.set import SetData from pyomo.core.base.units_container import units, pint_available, UnitsError from io import StringIO @@ -1487,7 +1487,7 @@ def test_domain_set_initializer(self): m.I = Set(initialize=[1, 2, 3]) param_vals = {1: 1, 2: 1, 3: -1} m.p = Param(m.I, initialize=param_vals, domain={-1, 1}) - self.assertIsInstance(m.p.domain, _SetData) + self.assertIsInstance(m.p.domain, SetData) @unittest.skipUnless(pint_available, "units test requires pint module") def test_set_value_units(self): diff --git a/pyomo/core/tests/unit/test_set.py b/pyomo/core/tests/unit/test_set.py index 38870d5213e..abd5a03c755 100644 --- a/pyomo/core/tests/unit/test_set.py +++ b/pyomo/core/tests/unit/test_set.py @@ -81,7 +81,7 @@ SetProduct_InfiniteSet, SetProduct_FiniteSet, SetProduct_OrderedSet, - _SetData, + SetData, FiniteSetData, InsertionOrderSetData, _SortedSetData, @@ -4300,7 +4300,7 @@ def _l_tri(model, i, j): # This tests a filter that matches the dimentionality of the # component. construct() needs to recognize that the filter is # returning a constant in construct() and re-assign it to be the - # _filter for each _SetData + # _filter for each SetData def _lt_3(model, i): self.assertIs(model, m) return i < 3 @@ -5297,15 +5297,15 @@ def test_no_normalize_index(self): class TestAbstractSetAPI(unittest.TestCase): - def test_SetData(self): + def testSetData(self): # This tests an anstract non-finite set API m = ConcreteModel() m.I = Set(initialize=[1]) - s = _SetData(m.I) + s = SetData(m.I) # - # _SetData API + # SetData API # with self.assertRaises(DeveloperError): @@ -5395,7 +5395,7 @@ def test_SetData(self): def test_FiniteMixin(self): # This tests an anstract finite set API - class FiniteMixin(_FiniteSetMixin, _SetData): + class FiniteMixin(_FiniteSetMixin, SetData): pass m = ConcreteModel() @@ -5403,7 +5403,7 @@ class FiniteMixin(_FiniteSetMixin, _SetData): s = FiniteMixin(m.I) # - # _SetData API + # SetData API # with self.assertRaises(DeveloperError): @@ -5520,7 +5520,7 @@ class FiniteMixin(_FiniteSetMixin, _SetData): def test_OrderedMixin(self): # This tests an anstract ordered set API - class OrderedMixin(_OrderedSetMixin, _FiniteSetMixin, _SetData): + class OrderedMixin(_OrderedSetMixin, _FiniteSetMixin, SetData): pass m = ConcreteModel() @@ -5528,7 +5528,7 @@ class OrderedMixin(_OrderedSetMixin, _FiniteSetMixin, _SetData): s = OrderedMixin(m.I) # - # _SetData API + # SetData API # with self.assertRaises(DeveloperError): From 43c7c40b032a5d3ef8512d8a9d54969d52f9e45a Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:56:14 -0600 Subject: [PATCH 27/83] Renamed _SortedSetData -> SortedSetData --- pyomo/core/base/set.py | 27 ++++++++++++++++----------- pyomo/core/tests/unit/test_set.py | 8 ++++---- 2 files changed, 20 insertions(+), 15 deletions(-) diff --git a/pyomo/core/base/set.py b/pyomo/core/base/set.py index 3280f512e83..d94cc86cf7c 100644 --- a/pyomo/core/base/set.py +++ b/pyomo/core/base/set.py @@ -1649,7 +1649,7 @@ class OrderedSetData(_OrderedSetMixin, FiniteSetData): implements a set ordered by insertion order, we make the "official" InsertionOrderSetData an empty derivative class, so that - issubclass(_SortedSetData, InsertionOrderSetData) == False + issubclass(SortedSetData, InsertionOrderSetData) == False Constructor Arguments: component The Set object that owns this data. @@ -1796,7 +1796,7 @@ def sorted_iter(self): return iter(self) -class _SortedSetData(_SortedSetMixin, OrderedSetData): +class SortedSetData(_SortedSetMixin, OrderedSetData): """ This class defines the data for a sorted set. @@ -1819,12 +1819,12 @@ def _iter_impl(self): """ if not self._is_sorted: self._sort() - return super(_SortedSetData, self)._iter_impl() + return super(SortedSetData, self)._iter_impl() def __reversed__(self): if not self._is_sorted: self._sort() - return super(_SortedSetData, self).__reversed__() + return super(SortedSetData, self).__reversed__() def _add_impl(self, value): # Note that the sorted status has no bearing on insertion, @@ -1838,7 +1838,7 @@ def _add_impl(self, value): # def discard(self, val): def clear(self): - super(_SortedSetData, self).clear() + super(SortedSetData, self).clear() self._is_sorted = True def at(self, index): @@ -1850,7 +1850,7 @@ def at(self, index): """ if not self._is_sorted: self._sort() - return super(_SortedSetData, self).at(index) + return super(SortedSetData, self).at(index) def ord(self, item): """ @@ -1862,7 +1862,7 @@ def ord(self, item): """ if not self._is_sorted: self._sort() - return super(_SortedSetData, self).ord(item) + return super(SortedSetData, self).ord(item) def sorted_data(self): return self.data() @@ -1875,6 +1875,11 @@ def _sort(self): self._is_sorted = True +class _SortedSetData(metaclass=RenamedClass): + __renamed__new_class__ = SortedSetData + __renamed__version__ = '6.7.2.dev0' + + ############################################################################ _SET_API = (('__contains__', 'test membership in'), 'get', 'ranges', 'bounds') @@ -2005,7 +2010,7 @@ def __new__(cls, *args, **kwds): # Many things are easier by forcing it to be consistent across # the set (namely, the _ComponentDataClass is constant). # However, it is a bit off that 'ordered' it the only arg NOT - # processed by Initializer. We can mock up a _SortedSetData + # processed by Initializer. We can mock up a SortedSetData # sort function that preserves Insertion Order (lambda x: x), but # the unsorted is harder (it would effectively be insertion # order, but ordered() may not be deterministic based on how the @@ -2052,7 +2057,7 @@ def __new__(cls, *args, **kwds): if ordered is Set.InsertionOrder: newObj._ComponentDataClass = InsertionOrderSetData elif ordered is Set.SortedOrder: - newObj._ComponentDataClass = _SortedSetData + newObj._ComponentDataClass = SortedSetData else: newObj._ComponentDataClass = FiniteSetData return newObj @@ -2435,13 +2440,13 @@ class OrderedSimpleSet(metaclass=RenamedClass): __renamed__version__ = '6.0' -class SortedScalarSet(_ScalarOrderedSetMixin, _SortedSetData, Set): +class SortedScalarSet(_ScalarOrderedSetMixin, SortedSetData, Set): def __init__(self, **kwds): # In case someone inherits from us, we will provide a rational # default for the "ordered" flag kwds.setdefault('ordered', Set.SortedOrder) - _SortedSetData.__init__(self, component=self) + SortedSetData.__init__(self, component=self) Set.__init__(self, **kwds) self._index = UnindexedComponent_index diff --git a/pyomo/core/tests/unit/test_set.py b/pyomo/core/tests/unit/test_set.py index abd5a03c755..f62589a6873 100644 --- a/pyomo/core/tests/unit/test_set.py +++ b/pyomo/core/tests/unit/test_set.py @@ -84,7 +84,7 @@ SetData, FiniteSetData, InsertionOrderSetData, - _SortedSetData, + SortedSetData, _FiniteSetMixin, _OrderedSetMixin, SetInitializer, @@ -4173,9 +4173,9 @@ def test_indexed_set(self): self.assertTrue(m.I[1].isordered()) self.assertTrue(m.I[2].isordered()) self.assertTrue(m.I[3].isordered()) - self.assertIs(type(m.I[1]), _SortedSetData) - self.assertIs(type(m.I[2]), _SortedSetData) - self.assertIs(type(m.I[3]), _SortedSetData) + self.assertIs(type(m.I[1]), SortedSetData) + self.assertIs(type(m.I[2]), SortedSetData) + self.assertIs(type(m.I[3]), SortedSetData) self.assertEqual(m.I.data(), {1: (2, 4, 5), 2: (2, 4, 5), 3: (2, 4, 5)}) # Explicit (procedural) construction From 63152a0be76006ff10e5f82f1b42de8af0ed6d56 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:57:39 -0600 Subject: [PATCH 28/83] Renamed _SOSConstraintData -> SOSConstraintData --- pyomo/contrib/appsi/base.py | 12 ++++++------ pyomo/contrib/appsi/fbbt.py | 6 +++--- pyomo/contrib/appsi/solvers/gurobi.py | 8 ++++---- pyomo/contrib/appsi/solvers/highs.py | 6 +++--- pyomo/contrib/appsi/writers/lp_writer.py | 6 +++--- pyomo/contrib/appsi/writers/nl_writer.py | 6 +++--- pyomo/contrib/solver/gurobi.py | 8 ++++---- pyomo/contrib/solver/persistent.py | 12 ++++++------ pyomo/core/base/sos.py | 15 ++++++++++----- pyomo/repn/plugins/cpxlp.py | 2 +- .../solvers/plugins/solvers/gurobi_persistent.py | 2 +- 11 files changed, 44 insertions(+), 39 deletions(-) diff --git a/pyomo/contrib/appsi/base.py b/pyomo/contrib/appsi/base.py index e50d5201090..409c8e2596c 100644 --- a/pyomo/contrib/appsi/base.py +++ b/pyomo/contrib/appsi/base.py @@ -22,7 +22,7 @@ MutableMapping, ) from pyomo.core.base.constraint import GeneralConstraintData, Constraint -from pyomo.core.base.sos import _SOSConstraintData, SOSConstraint +from pyomo.core.base.sos import SOSConstraintData, SOSConstraint from pyomo.core.base.var import GeneralVarData, Var from pyomo.core.base.param import ParamData, Param from pyomo.core.base.block import BlockData, Block @@ -1034,10 +1034,10 @@ def add_constraints(self, cons: List[GeneralConstraintData]): v.fix() @abc.abstractmethod - def _add_sos_constraints(self, cons: List[_SOSConstraintData]): + def _add_sos_constraints(self, cons: List[SOSConstraintData]): pass - def add_sos_constraints(self, cons: List[_SOSConstraintData]): + def add_sos_constraints(self, cons: List[SOSConstraintData]): for con in cons: if con in self._vars_referenced_by_con: raise ValueError( @@ -1154,10 +1154,10 @@ def remove_constraints(self, cons: List[GeneralConstraintData]): del self._vars_referenced_by_con[con] @abc.abstractmethod - def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): + def _remove_sos_constraints(self, cons: List[SOSConstraintData]): pass - def remove_sos_constraints(self, cons: List[_SOSConstraintData]): + def remove_sos_constraints(self, cons: List[SOSConstraintData]): self._remove_sos_constraints(cons) for con in cons: if con not in self._vars_referenced_by_con: @@ -1339,7 +1339,7 @@ def update(self, timer: HierarchicalTimer = None): old_cons.append(c) else: assert (c.ctype is SOSConstraint) or ( - c.ctype is None and isinstance(c, _SOSConstraintData) + c.ctype is None and isinstance(c, SOSConstraintData) ) old_sos.append(c) self.remove_constraints(old_cons) diff --git a/pyomo/contrib/appsi/fbbt.py b/pyomo/contrib/appsi/fbbt.py index 7735318f8ba..122ca5f7ffd 100644 --- a/pyomo/contrib/appsi/fbbt.py +++ b/pyomo/contrib/appsi/fbbt.py @@ -21,7 +21,7 @@ from pyomo.core.base.var import GeneralVarData from pyomo.core.base.param import ParamData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.sos import _SOSConstraintData +from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.objective import GeneralObjectiveData, minimize, maximize from pyomo.core.base.block import BlockData from pyomo.core.base import SymbolMap, TextLabeler @@ -169,7 +169,7 @@ def _add_constraints(self, cons: List[GeneralConstraintData]): for c, cc in self._con_map.items(): cc.name = self._symbol_map.getSymbol(c, self._con_labeler) - def _add_sos_constraints(self, cons: List[_SOSConstraintData]): + def _add_sos_constraints(self, cons: List[SOSConstraintData]): if len(cons) != 0: raise NotImplementedError( 'IntervalTightener does not support SOS constraints' @@ -184,7 +184,7 @@ def _remove_constraints(self, cons: List[GeneralConstraintData]): self._cmodel.remove_constraint(cc) del self._rcon_map[cc] - def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): + def _remove_sos_constraints(self, cons: List[SOSConstraintData]): if len(cons) != 0: raise NotImplementedError( 'IntervalTightener does not support SOS constraints' diff --git a/pyomo/contrib/appsi/solvers/gurobi.py b/pyomo/contrib/appsi/solvers/gurobi.py index 4392cdf0839..8606d44cd46 100644 --- a/pyomo/contrib/appsi/solvers/gurobi.py +++ b/pyomo/contrib/appsi/solvers/gurobi.py @@ -25,7 +25,7 @@ from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler from pyomo.core.base.var import Var, GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.sos import _SOSConstraintData +from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.param import ParamData from pyomo.core.expr.numvalue import value, is_constant, is_fixed, native_numeric_types from pyomo.repn import generate_standard_repn @@ -709,7 +709,7 @@ def _add_constraints(self, cons: List[GeneralConstraintData]): self._constraints_added_since_update.update(cons) self._needs_updated = True - def _add_sos_constraints(self, cons: List[_SOSConstraintData]): + def _add_sos_constraints(self, cons: List[SOSConstraintData]): for con in cons: conname = self._symbol_map.getSymbol(con, self._labeler) level = con.level @@ -749,7 +749,7 @@ def _remove_constraints(self, cons: List[GeneralConstraintData]): self._mutable_quadratic_helpers.pop(con, None) self._needs_updated = True - def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): + def _remove_sos_constraints(self, cons: List[SOSConstraintData]): for con in cons: if con in self._constraints_added_since_update: self._update_gurobi_model() @@ -1288,7 +1288,7 @@ def get_sos_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.sos._SOSConstraintData + con: pyomo.core.base.sos.SOSConstraintData The pyomo SOS constraint for which the corresponding gurobi SOS constraint attribute should be retrieved. attr: str diff --git a/pyomo/contrib/appsi/solvers/highs.py b/pyomo/contrib/appsi/solvers/highs.py index a6b7c102c91..5af7b297684 100644 --- a/pyomo/contrib/appsi/solvers/highs.py +++ b/pyomo/contrib/appsi/solvers/highs.py @@ -22,7 +22,7 @@ from pyomo.core.base import SymbolMap from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.sos import _SOSConstraintData +from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.param import ParamData from pyomo.core.expr.numvalue import value, is_constant from pyomo.repn import generate_standard_repn @@ -456,7 +456,7 @@ def _add_constraints(self, cons: List[GeneralConstraintData]): np.array(coef_values, dtype=np.double), ) - def _add_sos_constraints(self, cons: List[_SOSConstraintData]): + def _add_sos_constraints(self, cons: List[SOSConstraintData]): if cons: raise NotImplementedError( 'Highs interface does not support SOS constraints' @@ -487,7 +487,7 @@ def _remove_constraints(self, cons: List[GeneralConstraintData]): {v: k for k, v in self._pyomo_con_to_solver_con_map.items()} ) - def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): + def _remove_sos_constraints(self, cons: List[SOSConstraintData]): if cons: raise NotImplementedError( 'Highs interface does not support SOS constraints' diff --git a/pyomo/contrib/appsi/writers/lp_writer.py b/pyomo/contrib/appsi/writers/lp_writer.py index 3a168cdcd91..3a6682d5c00 100644 --- a/pyomo/contrib/appsi/writers/lp_writer.py +++ b/pyomo/contrib/appsi/writers/lp_writer.py @@ -14,7 +14,7 @@ from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData -from pyomo.core.base.sos import _SOSConstraintData +from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.block import BlockData from pyomo.repn.standard_repn import generate_standard_repn from pyomo.core.expr.numvalue import value @@ -102,7 +102,7 @@ def _add_params(self, params: List[ParamData]): def _add_constraints(self, cons: List[GeneralConstraintData]): cmodel.process_lp_constraints(cons, self) - def _add_sos_constraints(self, cons: List[_SOSConstraintData]): + def _add_sos_constraints(self, cons: List[SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('LP writer does not yet support SOS constraints') @@ -113,7 +113,7 @@ def _remove_constraints(self, cons: List[GeneralConstraintData]): self._symbol_map.removeSymbol(c) del self._solver_con_to_pyomo_con_map[cc] - def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): + def _remove_sos_constraints(self, cons: List[SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('LP writer does not yet support SOS constraints') diff --git a/pyomo/contrib/appsi/writers/nl_writer.py b/pyomo/contrib/appsi/writers/nl_writer.py index fced3c5ae10..c46cb1c0723 100644 --- a/pyomo/contrib/appsi/writers/nl_writer.py +++ b/pyomo/contrib/appsi/writers/nl_writer.py @@ -14,7 +14,7 @@ from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData -from pyomo.core.base.sos import _SOSConstraintData +from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.block import BlockData from pyomo.repn.standard_repn import generate_standard_repn from pyomo.core.expr.numvalue import value @@ -126,7 +126,7 @@ def _add_constraints(self, cons: List[GeneralConstraintData]): for c, cc in self._pyomo_con_to_solver_con_map.items(): cc.name = self._symbol_map.getSymbol(c, self._con_labeler) - def _add_sos_constraints(self, cons: List[_SOSConstraintData]): + def _add_sos_constraints(self, cons: List[SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('NL writer does not support SOS constraints') @@ -140,7 +140,7 @@ def _remove_constraints(self, cons: List[GeneralConstraintData]): self._writer.remove_constraint(cc) del self._solver_con_to_pyomo_con_map[cc] - def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): + def _remove_sos_constraints(self, cons: List[SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('NL writer does not support SOS constraints') diff --git a/pyomo/contrib/solver/gurobi.py b/pyomo/contrib/solver/gurobi.py index 107de15e625..c5a1c8c1cd8 100644 --- a/pyomo/contrib/solver/gurobi.py +++ b/pyomo/contrib/solver/gurobi.py @@ -24,7 +24,7 @@ from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler from pyomo.core.base.var import GeneralVarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.sos import _SOSConstraintData +from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.param import ParamData from pyomo.core.expr.numvalue import value, is_constant, is_fixed, native_numeric_types from pyomo.repn import generate_standard_repn @@ -685,7 +685,7 @@ def _add_constraints(self, cons: List[GeneralConstraintData]): self._constraints_added_since_update.update(cons) self._needs_updated = True - def _add_sos_constraints(self, cons: List[_SOSConstraintData]): + def _add_sos_constraints(self, cons: List[SOSConstraintData]): for con in cons: conname = self._symbol_map.getSymbol(con, self._labeler) level = con.level @@ -725,7 +725,7 @@ def _remove_constraints(self, cons: List[GeneralConstraintData]): self._mutable_quadratic_helpers.pop(con, None) self._needs_updated = True - def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): + def _remove_sos_constraints(self, cons: List[SOSConstraintData]): for con in cons: if con in self._constraints_added_since_update: self._update_gurobi_model() @@ -1218,7 +1218,7 @@ def get_sos_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.sos._SOSConstraintData + con: pyomo.core.base.sos.SOSConstraintData The pyomo SOS constraint for which the corresponding gurobi SOS constraint attribute should be retrieved. attr: str diff --git a/pyomo/contrib/solver/persistent.py b/pyomo/contrib/solver/persistent.py index 558b8cbf314..e98d76b4841 100644 --- a/pyomo/contrib/solver/persistent.py +++ b/pyomo/contrib/solver/persistent.py @@ -13,7 +13,7 @@ from typing import List from pyomo.core.base.constraint import GeneralConstraintData, Constraint -from pyomo.core.base.sos import _SOSConstraintData, SOSConstraint +from pyomo.core.base.sos import SOSConstraintData, SOSConstraint from pyomo.core.base.var import GeneralVarData from pyomo.core.base.param import ParamData, Param from pyomo.core.base.objective import GeneralObjectiveData @@ -130,10 +130,10 @@ def add_constraints(self, cons: List[GeneralConstraintData]): v.fix() @abc.abstractmethod - def _add_sos_constraints(self, cons: List[_SOSConstraintData]): + def _add_sos_constraints(self, cons: List[SOSConstraintData]): pass - def add_sos_constraints(self, cons: List[_SOSConstraintData]): + def add_sos_constraints(self, cons: List[SOSConstraintData]): for con in cons: if con in self._vars_referenced_by_con: raise ValueError( @@ -230,10 +230,10 @@ def remove_constraints(self, cons: List[GeneralConstraintData]): del self._vars_referenced_by_con[con] @abc.abstractmethod - def _remove_sos_constraints(self, cons: List[_SOSConstraintData]): + def _remove_sos_constraints(self, cons: List[SOSConstraintData]): pass - def remove_sos_constraints(self, cons: List[_SOSConstraintData]): + def remove_sos_constraints(self, cons: List[SOSConstraintData]): self._remove_sos_constraints(cons) for con in cons: if con not in self._vars_referenced_by_con: @@ -389,7 +389,7 @@ def update(self, timer: HierarchicalTimer = None): old_cons.append(c) else: assert (c.ctype is SOSConstraint) or ( - c.ctype is None and isinstance(c, _SOSConstraintData) + c.ctype is None and isinstance(c, SOSConstraintData) ) old_sos.append(c) self.remove_constraints(old_cons) diff --git a/pyomo/core/base/sos.py b/pyomo/core/base/sos.py index 6b8586c9b49..4a8afb05d71 100644 --- a/pyomo/core/base/sos.py +++ b/pyomo/core/base/sos.py @@ -28,7 +28,7 @@ logger = logging.getLogger('pyomo.core') -class _SOSConstraintData(ActiveComponentData): +class SOSConstraintData(ActiveComponentData): """ This class defines the data for a single special ordered set. @@ -101,6 +101,11 @@ def set_items(self, variables, weights): self._weights.append(w) +class _SOSConstraintData(metaclass=RenamedClass): + __renamed__new_class__ = SOSConstraintData + __renamed__version__ = '6.7.2.dev0' + + @ModelComponentFactory.register("SOS constraint expressions.") class SOSConstraint(ActiveIndexedComponent): """ @@ -512,10 +517,10 @@ def add(self, index, variables, weights=None): Add a component data for the specified index. """ if index is None: - # because ScalarSOSConstraint already makes an _SOSConstraintData instance + # because ScalarSOSConstraint already makes an SOSConstraintData instance soscondata = self else: - soscondata = _SOSConstraintData(self) + soscondata = SOSConstraintData(self) self._data[index] = soscondata soscondata._index = index @@ -549,9 +554,9 @@ def pprint(self, ostream=None, verbose=False, prefix=""): ostream.write("\t\t" + str(weight) + ' : ' + var.name + '\n') -class ScalarSOSConstraint(SOSConstraint, _SOSConstraintData): +class ScalarSOSConstraint(SOSConstraint, SOSConstraintData): def __init__(self, *args, **kwd): - _SOSConstraintData.__init__(self, self) + SOSConstraintData.__init__(self, self) SOSConstraint.__init__(self, *args, **kwd) self._index = UnindexedComponent_index diff --git a/pyomo/repn/plugins/cpxlp.py b/pyomo/repn/plugins/cpxlp.py index 46e6b6d5265..6228e7c7286 100644 --- a/pyomo/repn/plugins/cpxlp.py +++ b/pyomo/repn/plugins/cpxlp.py @@ -374,7 +374,7 @@ def _print_expr_canonical( def printSOS(self, symbol_map, labeler, variable_symbol_map, soscondata, output): """ - Prints the SOS constraint associated with the _SOSConstraintData object + Prints the SOS constraint associated with the SOSConstraintData object """ sos_template_string = self.sos_template_string diff --git a/pyomo/solvers/plugins/solvers/gurobi_persistent.py b/pyomo/solvers/plugins/solvers/gurobi_persistent.py index 8a81aad3d3e..585a78e3ef1 100644 --- a/pyomo/solvers/plugins/solvers/gurobi_persistent.py +++ b/pyomo/solvers/plugins/solvers/gurobi_persistent.py @@ -413,7 +413,7 @@ def get_sos_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.sos._SOSConstraintData + con: pyomo.core.base.sos.SOSConstraintData The pyomo SOS constraint for which the corresponding gurobi SOS constraint attribute should be retrieved. attr: str From 430f98207353b1e1e7383504aa0336bc852aeb9c Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 17:57:41 -0600 Subject: [PATCH 29/83] Renamed _SuffixData -> SuffixData --- pyomo/core/base/suffix.py | 4 ++-- pyomo/repn/plugins/nl_writer.py | 15 ++++++++++----- 2 files changed, 12 insertions(+), 7 deletions(-) diff --git a/pyomo/core/base/suffix.py b/pyomo/core/base/suffix.py index be2f732650d..c4b37789773 100644 --- a/pyomo/core/base/suffix.py +++ b/pyomo/core/base/suffix.py @@ -129,7 +129,7 @@ class SuffixDirection(enum.IntEnum): IMPORT_EXPORT = 3 -_SuffixDataTypeDomain = In(SuffixDataType) +SuffixDataTypeDomain = In(SuffixDataType) _SuffixDirectionDomain = In(SuffixDirection) @@ -253,7 +253,7 @@ def datatype(self): def datatype(self, datatype): """Set the suffix datatype.""" if datatype is not None: - datatype = _SuffixDataTypeDomain(datatype) + datatype = SuffixDataTypeDomain(datatype) self._datatype = datatype @property diff --git a/pyomo/repn/plugins/nl_writer.py b/pyomo/repn/plugins/nl_writer.py index c010cee5e54..1a49238f35b 100644 --- a/pyomo/repn/plugins/nl_writer.py +++ b/pyomo/repn/plugins/nl_writer.py @@ -423,7 +423,7 @@ def _generate_symbol_map(self, info): return symbol_map -class _SuffixData(object): +class SuffixData(object): def __init__(self, name): self.name = name self.obj = {} @@ -505,6 +505,11 @@ def compile(self, column_order, row_order, obj_order, model_id): ) +class _SuffixData(metaclass=RenamedClass): + __renamed__new_class__ = SuffixData + __renamed__version__ = '6.7.2.dev0' + + class CachingNumericSuffixFinder(SuffixFinder): scale = True @@ -637,7 +642,7 @@ def write(self, model): continue name = suffix.local_name if name not in suffix_data: - suffix_data[name] = _SuffixData(name) + suffix_data[name] = SuffixData(name) suffix_data[name].update(suffix) # # Data structures to support variable/constraint scaling @@ -994,7 +999,7 @@ def write(self, model): "model. To avoid this error please use only one of " "these methods to define special ordered sets." ) - suffix_data[name] = _SuffixData(name) + suffix_data[name] = SuffixData(name) suffix_data[name].datatype.add(Suffix.INT) sos_id = 0 sosno = suffix_data['sosno'] @@ -1344,7 +1349,7 @@ def write(self, model): if not _vals: continue ostream.write(f"S{_field|_float} {len(_vals)} {name}\n") - # Note: _SuffixData.compile() guarantees the value is int/float + # Note: SuffixData.compile() guarantees the value is int/float ostream.write( ''.join(f"{_id} {_vals[_id]!r}\n" for _id in sorted(_vals)) ) @@ -1454,7 +1459,7 @@ def write(self, model): logger.warning("ignoring 'dual' suffix for Model") if data.con: ostream.write(f"d{len(data.con)}\n") - # Note: _SuffixData.compile() guarantees the value is int/float + # Note: SuffixData.compile() guarantees the value is int/float ostream.write( ''.join(f"{_id} {data.con[_id]!r}\n" for _id in sorted(data.con)) ) From f810600f0520097052fb4bf483920b86d03c80fb Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 18:02:15 -0600 Subject: [PATCH 30/83] Renamed _VarData -> VarData --- pyomo/common/tests/test_timing.py | 4 +-- .../fme/fourier_motzkin_elimination.py | 4 +-- pyomo/contrib/gdp_bounds/info.py | 2 +- .../algorithms/solvers/pyomo_ext_cyipopt.py | 10 +++---- pyomo/contrib/pyros/config.py | 8 ++--- .../contrib/pyros/pyros_algorithm_methods.py | 2 +- pyomo/contrib/pyros/tests/test_config.py | 16 +++++----- pyomo/contrib/pyros/tests/test_grcs.py | 4 +-- pyomo/contrib/pyros/util.py | 6 ++-- pyomo/core/base/__init__.py | 2 +- pyomo/core/base/boolean_var.py | 4 +-- pyomo/core/base/piecewise.py | 16 +++++----- pyomo/core/base/var.py | 29 +++++++++++-------- pyomo/core/beta/dict_objects.py | 4 +-- pyomo/core/beta/list_objects.py | 4 +-- pyomo/core/expr/numeric_expr.py | 2 +- .../plugins/transform/eliminate_fixed_vars.py | 4 +-- .../plugins/transform/radix_linearization.py | 6 ++-- pyomo/core/tests/unit/test_piecewise.py | 2 +- pyomo/core/tests/unit/test_var_set_bounds.py | 2 +- pyomo/dae/misc.py | 2 +- pyomo/repn/plugins/ampl/ampl_.py | 10 +++---- pyomo/repn/plugins/cpxlp.py | 2 +- pyomo/repn/plugins/mps.py | 2 +- pyomo/repn/plugins/nl_writer.py | 10 +++---- pyomo/repn/plugins/standard_form.py | 6 ++-- .../plugins/solvers/cplex_persistent.py | 4 +-- .../plugins/solvers/gurobi_persistent.py | 4 +-- .../plugins/solvers/mosek_persistent.py | 4 +-- .../plugins/solvers/persistent_solver.py | 4 +-- .../plugins/solvers/xpress_persistent.py | 4 +-- pyomo/util/calc_var_value.py | 2 +- 32 files changed, 95 insertions(+), 90 deletions(-) diff --git a/pyomo/common/tests/test_timing.py b/pyomo/common/tests/test_timing.py index 48288746882..90f4cdcd034 100644 --- a/pyomo/common/tests/test_timing.py +++ b/pyomo/common/tests/test_timing.py @@ -35,7 +35,7 @@ Any, TransformationFactory, ) -from pyomo.core.base.var import _VarData +from pyomo.core.base.var import VarData class _pseudo_component(Var): @@ -62,7 +62,7 @@ def test_raw_construction_timer(self): ) v = Var() v.construct() - a = ConstructionTimer(_VarData(v)) + a = ConstructionTimer(VarData(v)) self.assertRegex( str(a), r"ConstructionTimer object for Var ScalarVar\[NOTSET\]; " diff --git a/pyomo/contrib/fme/fourier_motzkin_elimination.py b/pyomo/contrib/fme/fourier_motzkin_elimination.py index a1b5d744cf4..4636450c58e 100644 --- a/pyomo/contrib/fme/fourier_motzkin_elimination.py +++ b/pyomo/contrib/fme/fourier_motzkin_elimination.py @@ -23,7 +23,7 @@ value, ConstraintList, ) -from pyomo.core.base import TransformationFactory, _VarData +from pyomo.core.base import TransformationFactory, VarData from pyomo.core.plugins.transform.hierarchy import Transformation from pyomo.common.config import ConfigBlock, ConfigValue, NonNegativeFloat from pyomo.common.modeling import unique_component_name @@ -58,7 +58,7 @@ def _check_var_bounds_filter(constraint): def vars_to_eliminate_list(x): - if isinstance(x, (Var, _VarData)): + if isinstance(x, (Var, VarData)): if not x.is_indexed(): return ComponentSet([x]) ans = ComponentSet() diff --git a/pyomo/contrib/gdp_bounds/info.py b/pyomo/contrib/gdp_bounds/info.py index db3f6d0846d..e65df2bfab0 100644 --- a/pyomo/contrib/gdp_bounds/info.py +++ b/pyomo/contrib/gdp_bounds/info.py @@ -35,7 +35,7 @@ def disjunctive_bound(var, scope): """Compute the disjunctive bounds for a variable in a given scope. Args: - var (_VarData): Variable for which to compute bound + var (VarData): Variable for which to compute bound scope (Component): The scope in which to compute the bound. If not a DisjunctData, it will walk up the tree and use the scope of the most immediate enclosing DisjunctData. diff --git a/pyomo/contrib/pynumero/algorithms/solvers/pyomo_ext_cyipopt.py b/pyomo/contrib/pynumero/algorithms/solvers/pyomo_ext_cyipopt.py index 16c5a19a5c6..7f43f6ac7c0 100644 --- a/pyomo/contrib/pynumero/algorithms/solvers/pyomo_ext_cyipopt.py +++ b/pyomo/contrib/pynumero/algorithms/solvers/pyomo_ext_cyipopt.py @@ -16,7 +16,7 @@ from pyomo.contrib.pynumero.interfaces.pyomo_nlp import PyomoNLP from pyomo.contrib.pynumero.sparse.block_vector import BlockVector from pyomo.environ import Var, Constraint, value -from pyomo.core.base.var import _VarData +from pyomo.core.base.var import VarData from pyomo.common.modeling import unique_component_name """ @@ -109,12 +109,12 @@ def __init__( An instance of a derived class (from ExternalInputOutputModel) that provides the methods to compute the outputs and the derivatives. - inputs : list of Pyomo variables (_VarData) + inputs : list of Pyomo variables (VarData) The Pyomo model needs to have variables to represent the inputs to the external model. This is the list of those input variables in the order that corresponds to the input_values vector provided in the set_inputs call. - outputs : list of Pyomo variables (_VarData) + outputs : list of Pyomo variables (VarData) The Pyomo model needs to have variables to represent the outputs from the external model. This is the list of those output variables in the order that corresponds to the numpy array returned from the evaluate_outputs call. @@ -130,7 +130,7 @@ def __init__( # verify that the inputs and outputs were passed correctly self._inputs = [v for v in inputs] for v in self._inputs: - if not isinstance(v, _VarData): + if not isinstance(v, VarData): raise RuntimeError( 'Argument inputs passed to PyomoExternalCyIpoptProblem must be' ' a list of VarData objects. Note: if you have an indexed variable, pass' @@ -139,7 +139,7 @@ def __init__( self._outputs = [v for v in outputs] for v in self._outputs: - if not isinstance(v, _VarData): + if not isinstance(v, VarData): raise RuntimeError( 'Argument outputs passed to PyomoExternalCyIpoptProblem must be' ' a list of VarData objects. Note: if you have an indexed variable, pass' diff --git a/pyomo/contrib/pyros/config.py b/pyomo/contrib/pyros/config.py index e60b474d037..59bf9a9ab37 100644 --- a/pyomo/contrib/pyros/config.py +++ b/pyomo/contrib/pyros/config.py @@ -16,7 +16,7 @@ Path, ) from pyomo.common.errors import ApplicationError, PyomoException -from pyomo.core.base import Var, _VarData +from pyomo.core.base import Var, VarData from pyomo.core.base.param import Param, ParamData from pyomo.opt import SolverFactory from pyomo.contrib.pyros.util import ObjectiveType, setup_pyros_logger @@ -98,7 +98,7 @@ class InputDataStandardizer(object): Pyomo component type, such as Component, Var or Param. cdatatype : type Corresponding Pyomo component data type, such as - _ComponentData, _VarData, or ParamData. + _ComponentData, VarData, or ParamData. ctype_validator : callable, optional Validator function for objects of type `ctype`. cdatatype_validator : callable, optional @@ -511,7 +511,7 @@ def pyros_config(): "first_stage_variables", ConfigValue( default=[], - domain=InputDataStandardizer(Var, _VarData, allow_repeats=False), + domain=InputDataStandardizer(Var, VarData, allow_repeats=False), description="First-stage (or design) variables.", visibility=1, ), @@ -520,7 +520,7 @@ def pyros_config(): "second_stage_variables", ConfigValue( default=[], - domain=InputDataStandardizer(Var, _VarData, allow_repeats=False), + domain=InputDataStandardizer(Var, VarData, allow_repeats=False), description="Second-stage (or control) variables.", visibility=1, ), diff --git a/pyomo/contrib/pyros/pyros_algorithm_methods.py b/pyomo/contrib/pyros/pyros_algorithm_methods.py index 5987db074e6..cfb57b08c7f 100644 --- a/pyomo/contrib/pyros/pyros_algorithm_methods.py +++ b/pyomo/contrib/pyros/pyros_algorithm_methods.py @@ -28,7 +28,7 @@ from pyomo.core.base import value from pyomo.core.expr import MonomialTermExpression from pyomo.common.collections import ComponentSet, ComponentMap -from pyomo.core.base.var import _VarData as VarData +from pyomo.core.base.var import VarData as VarData from itertools import chain from pyomo.common.dependencies import numpy as np diff --git a/pyomo/contrib/pyros/tests/test_config.py b/pyomo/contrib/pyros/tests/test_config.py index cd635e795fc..166fbada4ff 100644 --- a/pyomo/contrib/pyros/tests/test_config.py +++ b/pyomo/contrib/pyros/tests/test_config.py @@ -5,7 +5,7 @@ import logging import unittest -from pyomo.core.base import ConcreteModel, Var, _VarData +from pyomo.core.base import ConcreteModel, Var, VarData from pyomo.common.log import LoggingIntercept from pyomo.common.errors import ApplicationError from pyomo.core.base.param import Param, ParamData @@ -38,7 +38,7 @@ def test_single_component_data(self): mdl = ConcreteModel() mdl.v = Var([0, 1]) - standardizer_func = InputDataStandardizer(Var, _VarData) + standardizer_func = InputDataStandardizer(Var, VarData) standardizer_input = mdl.v[0] standardizer_output = standardizer_func(standardizer_input) @@ -74,7 +74,7 @@ def test_standardizer_indexed_component(self): mdl = ConcreteModel() mdl.v = Var([0, 1]) - standardizer_func = InputDataStandardizer(Var, _VarData) + standardizer_func = InputDataStandardizer(Var, VarData) standardizer_input = mdl.v standardizer_output = standardizer_func(standardizer_input) @@ -113,7 +113,7 @@ def test_standardizer_multiple_components(self): mdl.v = Var([0, 1]) mdl.x = Var(["a", "b"]) - standardizer_func = InputDataStandardizer(Var, _VarData) + standardizer_func = InputDataStandardizer(Var, VarData) standardizer_input = [mdl.v[0], mdl.x] standardizer_output = standardizer_func(standardizer_input) @@ -154,7 +154,7 @@ def test_standardizer_invalid_duplicates(self): mdl.v = Var([0, 1]) mdl.x = Var(["a", "b"]) - standardizer_func = InputDataStandardizer(Var, _VarData, allow_repeats=False) + standardizer_func = InputDataStandardizer(Var, VarData, allow_repeats=False) exc_str = r"Standardized.*list.*contains duplicate entries\." with self.assertRaisesRegex(ValueError, exc_str): @@ -165,7 +165,7 @@ def test_standardizer_invalid_type(self): Test standardizer raises exception as expected when input is of invalid type. """ - standardizer_func = InputDataStandardizer(Var, _VarData) + standardizer_func = InputDataStandardizer(Var, VarData) exc_str = r"Input object .*is not of valid component type.*" with self.assertRaisesRegex(TypeError, exc_str): @@ -178,7 +178,7 @@ def test_standardizer_iterable_with_invalid_type(self): """ mdl = ConcreteModel() mdl.v = Var([0, 1]) - standardizer_func = InputDataStandardizer(Var, _VarData) + standardizer_func = InputDataStandardizer(Var, VarData) exc_str = r"Input object .*entry of iterable.*is not of valid component type.*" with self.assertRaisesRegex(TypeError, exc_str): @@ -189,7 +189,7 @@ def test_standardizer_invalid_str_passed(self): Test standardizer raises exception as expected when input is of invalid type str. """ - standardizer_func = InputDataStandardizer(Var, _VarData) + standardizer_func = InputDataStandardizer(Var, VarData) exc_str = r"Input object .*is not of valid component type.*" with self.assertRaisesRegex(TypeError, exc_str): diff --git a/pyomo/contrib/pyros/tests/test_grcs.py b/pyomo/contrib/pyros/tests/test_grcs.py index c308f0d6990..8093e93c8ef 100644 --- a/pyomo/contrib/pyros/tests/test_grcs.py +++ b/pyomo/contrib/pyros/tests/test_grcs.py @@ -19,7 +19,7 @@ from pyomo.common.collections import ComponentSet, ComponentMap from pyomo.common.config import ConfigBlock, ConfigValue from pyomo.core.base.set_types import NonNegativeIntegers -from pyomo.core.base.var import _VarData +from pyomo.core.base.var import VarData from pyomo.core.expr import ( identify_variables, identify_mutable_parameters, @@ -592,7 +592,7 @@ def test_dr_eqns_form_correct(self): param_product_multiplicand = term.args[0] dr_var_multiplicand = term.args[1] else: - self.assertIsInstance(term, _VarData) + self.assertIsInstance(term, VarData) param_product_multiplicand = 1 dr_var_multiplicand = term diff --git a/pyomo/contrib/pyros/util.py b/pyomo/contrib/pyros/util.py index a3ab3464aa8..65fb0a2c6aa 100644 --- a/pyomo/contrib/pyros/util.py +++ b/pyomo/contrib/pyros/util.py @@ -832,7 +832,7 @@ def get_state_vars(blk, first_stage_variables, second_stage_variables): Get state variables of a modeling block. The state variables with respect to `blk` are the unfixed - `_VarData` objects participating in the active objective + `VarData` objects participating in the active objective or constraints descended from `blk` which are not first-stage variables or second-stage variables. @@ -847,7 +847,7 @@ def get_state_vars(blk, first_stage_variables, second_stage_variables): Yields ------ - _VarData + VarData State variable. """ dof_var_set = ComponentSet(first_stage_variables) | ComponentSet( @@ -954,7 +954,7 @@ def validate_variable_partitioning(model, config): Returns ------- - list of _VarData + list of VarData State variables of the model. Raises diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 408cf16c00e..0363380af1f 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -57,7 +57,7 @@ from pyomo.core.base.check import BuildCheck from pyomo.core.base.set import Set, SetOf, simple_set_rule, RangeSet from pyomo.core.base.param import Param -from pyomo.core.base.var import Var, _VarData, GeneralVarData, ScalarVar, VarList +from pyomo.core.base.var import Var, VarData, GeneralVarData, ScalarVar, VarList from pyomo.core.base.boolean_var import ( BooleanVar, BooleanVarData, diff --git a/pyomo/core/base/boolean_var.py b/pyomo/core/base/boolean_var.py index 287851a7f7e..925dca530a7 100644 --- a/pyomo/core/base/boolean_var.py +++ b/pyomo/core/base/boolean_var.py @@ -270,14 +270,14 @@ def stale(self, val): self._stale = StaleFlagManager.get_flag(0) def get_associated_binary(self): - """Get the binary _VarData associated with this + """Get the binary VarData associated with this GeneralBooleanVarData""" return ( self._associated_binary() if self._associated_binary is not None else None ) def associate_binary_var(self, binary_var): - """Associate a binary _VarData to this GeneralBooleanVarData""" + """Associate a binary VarData to this GeneralBooleanVarData""" if ( self._associated_binary is not None and type(self._associated_binary) diff --git a/pyomo/core/base/piecewise.py b/pyomo/core/base/piecewise.py index 43f8ddbfef5..f061ebfbdc8 100644 --- a/pyomo/core/base/piecewise.py +++ b/pyomo/core/base/piecewise.py @@ -47,7 +47,7 @@ from pyomo.core.base.component import ModelComponentFactory from pyomo.core.base.constraint import Constraint, ConstraintList from pyomo.core.base.sos import SOSConstraint -from pyomo.core.base.var import Var, _VarData, IndexedVar +from pyomo.core.base.var import Var, VarData, IndexedVar from pyomo.core.base.set_types import PositiveReals, NonNegativeReals, Binary from pyomo.core.base.util import flatten_tuple @@ -1240,7 +1240,7 @@ def __init__(self, *args, **kwds): # Check that the variables args are actually Pyomo Vars if not ( - isinstance(self._domain_var, _VarData) + isinstance(self._domain_var, VarData) or isinstance(self._domain_var, IndexedVar) ): msg = ( @@ -1249,7 +1249,7 @@ def __init__(self, *args, **kwds): ) raise TypeError(msg % (repr(self._domain_var),)) if not ( - isinstance(self._range_var, _VarData) + isinstance(self._range_var, VarData) or isinstance(self._range_var, IndexedVar) ): msg = ( @@ -1359,22 +1359,22 @@ def add(self, index, _is_indexed=None): _self_yvar = None _self_domain_pts_index = None if not _is_indexed: - # allows one to mix Var and _VarData as input to + # allows one to mix Var and VarData as input to # non-indexed Piecewise, index would be None in this case - # so for Var elements Var[None] is Var, but _VarData[None] would fail + # so for Var elements Var[None] is Var, but VarData[None] would fail _self_xvar = self._domain_var _self_yvar = self._range_var _self_domain_pts_index = self._domain_points[index] else: - # The following allows one to specify a Var or _VarData + # The following allows one to specify a Var or VarData # object even with an indexed Piecewise component. # The most common situation will most likely be a VarArray, # so we try this first. - if not isinstance(self._domain_var, _VarData): + if not isinstance(self._domain_var, VarData): _self_xvar = self._domain_var[index] else: _self_xvar = self._domain_var - if not isinstance(self._range_var, _VarData): + if not isinstance(self._range_var, VarData): _self_yvar = self._range_var[index] else: _self_yvar = self._range_var diff --git a/pyomo/core/base/var.py b/pyomo/core/base/var.py index 0e45ad44225..509238e4e6b 100644 --- a/pyomo/core/base/var.py +++ b/pyomo/core/base/var.py @@ -88,7 +88,7 @@ ) -class _VarData(ComponentData, NumericValue): +class VarData(ComponentData, NumericValue): """This class defines the abstract interface for a single variable. Note that this "abstract" class is not intended to be directly @@ -319,7 +319,12 @@ def free(self): return self.unfix() -class GeneralVarData(_VarData): +class _VarData(metaclass=RenamedClass): + __renamed__new_class__ = VarData + __renamed__version__ = '6.7.2.dev0' + + +class GeneralVarData(VarData): """This class defines the data for a single variable.""" __slots__ = ('_value', '_lb', '_ub', '_domain', '_fixed', '_stale') @@ -329,7 +334,7 @@ def __init__(self, component=None): # # These lines represent in-lining of the # following constructors: - # - _VarData + # - VarData # - ComponentData # - NumericValue self._component = weakref_ref(component) if (component is not None) else None @@ -448,9 +453,9 @@ def domain(self, domain): ) raise - @_VarData.bounds.getter + @VarData.bounds.getter def bounds(self): - # Custom implementation of _VarData.bounds to avoid unnecessary + # Custom implementation of VarData.bounds to avoid unnecessary # expression generation and duplicate calls to domain.bounds() domain_lb, domain_ub = self.domain.bounds() # lb is the tighter of the domain and bounds @@ -491,9 +496,9 @@ def bounds(self): ub = min(ub, domain_ub) return lb, ub - @_VarData.lb.getter + @VarData.lb.getter def lb(self): - # Custom implementation of _VarData.lb to avoid unnecessary + # Custom implementation of VarData.lb to avoid unnecessary # expression generation domain_lb, domain_ub = self.domain.bounds() # lb is the tighter of the domain and bounds @@ -516,9 +521,9 @@ def lb(self): lb = max(lb, domain_lb) return lb - @_VarData.ub.getter + @VarData.ub.getter def ub(self): - # Custom implementation of _VarData.ub to avoid unnecessary + # Custom implementation of VarData.ub to avoid unnecessary # expression generation domain_lb, domain_ub = self.domain.bounds() # ub is the tighter of the domain and bounds @@ -780,7 +785,7 @@ def add(self, index): def construct(self, data=None): """ - Construct the _VarData objects for this variable + Construct the VarData objects for this variable """ if self._constructed: return @@ -839,7 +844,7 @@ def construct(self, data=None): # initializers that are constant, we can avoid # re-calling (and re-validating) the inputs in certain # cases. To support this, we will create the first - # _VarData and then use it as a template to initialize + # VarData and then use it as a template to initialize # (constant portions of) every VarData so as to not # repeat all the domain/bounds validation. try: @@ -1008,7 +1013,7 @@ def fix(self, value=NOTSET, skip_validation=False): def unfix(self): """Unfix all variables in this :class:`IndexedVar` (treat as variable) - This sets the :attr:`_VarData.fixed` indicator to False for + This sets the :attr:`VarData.fixed` indicator to False for every variable in this :class:`IndexedVar`. """ diff --git a/pyomo/core/beta/dict_objects.py b/pyomo/core/beta/dict_objects.py index 7c44166f189..eedb3c45bf3 100644 --- a/pyomo/core/beta/dict_objects.py +++ b/pyomo/core/beta/dict_objects.py @@ -14,7 +14,7 @@ from pyomo.common.log import is_debug_set from pyomo.core.base.set_types import Any -from pyomo.core.base.var import IndexedVar, _VarData +from pyomo.core.base.var import IndexedVar, VarData from pyomo.core.base.constraint import IndexedConstraint, ConstraintData from pyomo.core.base.objective import IndexedObjective, ObjectiveData from pyomo.core.base.expression import IndexedExpression, ExpressionData @@ -184,7 +184,7 @@ def __init__(self, *args, **kwds): # Constructor for ComponentDict needs to # go last in order to handle any initialization # iterable as an argument - ComponentDict.__init__(self, _VarData, *args, **kwds) + ComponentDict.__init__(self, VarData, *args, **kwds) class ConstraintDict(ComponentDict, IndexedConstraint): diff --git a/pyomo/core/beta/list_objects.py b/pyomo/core/beta/list_objects.py index d10a30e18e2..005bfc38a1f 100644 --- a/pyomo/core/beta/list_objects.py +++ b/pyomo/core/beta/list_objects.py @@ -14,7 +14,7 @@ from pyomo.common.log import is_debug_set from pyomo.core.base.set_types import Any -from pyomo.core.base.var import IndexedVar, _VarData +from pyomo.core.base.var import IndexedVar, VarData from pyomo.core.base.constraint import IndexedConstraint, ConstraintData from pyomo.core.base.objective import IndexedObjective, ObjectiveData from pyomo.core.base.expression import IndexedExpression, ExpressionData @@ -232,7 +232,7 @@ def __init__(self, *args, **kwds): # Constructor for ComponentList needs to # go last in order to handle any initialization # iterable as an argument - ComponentList.__init__(self, _VarData, *args, **kwds) + ComponentList.__init__(self, VarData, *args, **kwds) class XConstraintList(ComponentList, IndexedConstraint): diff --git a/pyomo/core/expr/numeric_expr.py b/pyomo/core/expr/numeric_expr.py index 25d83ca20f4..50abaeedbba 100644 --- a/pyomo/core/expr/numeric_expr.py +++ b/pyomo/core/expr/numeric_expr.py @@ -1238,7 +1238,7 @@ class LinearExpression(SumExpression): - not potentially variable (e.g., native types, Params, or NPV expressions) - :py:class:`MonomialTermExpression` - - :py:class:`_VarData` + - :py:class:`VarData` Args: args (tuple): Children nodes diff --git a/pyomo/core/plugins/transform/eliminate_fixed_vars.py b/pyomo/core/plugins/transform/eliminate_fixed_vars.py index 9312035b8c8..934228afd7c 100644 --- a/pyomo/core/plugins/transform/eliminate_fixed_vars.py +++ b/pyomo/core/plugins/transform/eliminate_fixed_vars.py @@ -11,7 +11,7 @@ from pyomo.core.expr import ExpressionBase, as_numeric from pyomo.core import Constraint, Objective, TransformationFactory -from pyomo.core.base.var import Var, _VarData +from pyomo.core.base.var import Var, VarData from pyomo.core.util import sequence from pyomo.core.plugins.transform.hierarchy import IsomorphicTransformation @@ -77,7 +77,7 @@ def _fix_vars(self, expr, model): if isinstance(expr._args[i], ExpressionBase): _args.append(self._fix_vars(expr._args[i], model)) elif ( - isinstance(expr._args[i], Var) or isinstance(expr._args[i], _VarData) + isinstance(expr._args[i], Var) or isinstance(expr._args[i], VarData) ) and expr._args[i].fixed: if expr._args[i].value != 0.0: _args.append(as_numeric(expr._args[i].value)) diff --git a/pyomo/core/plugins/transform/radix_linearization.py b/pyomo/core/plugins/transform/radix_linearization.py index c67e556d60c..92270655f31 100644 --- a/pyomo/core/plugins/transform/radix_linearization.py +++ b/pyomo/core/plugins/transform/radix_linearization.py @@ -21,7 +21,7 @@ Block, RangeSet, ) -from pyomo.core.base.var import _VarData +from pyomo.core.base.var import VarData import logging @@ -268,8 +268,8 @@ def _collect_bilinear(self, expr, bilin, quad): self._collect_bilinear(e, bilin, quad) # No need to check denominator, as this is poly_degree==2 return - if not isinstance(expr._numerator[0], _VarData) or not isinstance( - expr._numerator[1], _VarData + if not isinstance(expr._numerator[0], VarData) or not isinstance( + expr._numerator[1], VarData ): raise RuntimeError("Cannot yet handle complex subexpressions") if expr._numerator[0] is expr._numerator[1]: diff --git a/pyomo/core/tests/unit/test_piecewise.py b/pyomo/core/tests/unit/test_piecewise.py index af82ef7c06d..7b8e01e6a45 100644 --- a/pyomo/core/tests/unit/test_piecewise.py +++ b/pyomo/core/tests/unit/test_piecewise.py @@ -104,7 +104,7 @@ def test_indexed_with_nonindexed_vars(self): model.con3 = Piecewise(*args, **keywords) # test that nonindexed Piecewise can handle - # _VarData (e.g model.x[1] + # VarData (e.g model.x[1] def test_nonindexed_with_indexed_vars(self): model = ConcreteModel() model.range = Var([1]) diff --git a/pyomo/core/tests/unit/test_var_set_bounds.py b/pyomo/core/tests/unit/test_var_set_bounds.py index bae89556ce3..1686ba4f1c6 100644 --- a/pyomo/core/tests/unit/test_var_set_bounds.py +++ b/pyomo/core/tests/unit/test_var_set_bounds.py @@ -36,7 +36,7 @@ # GAH: These tests been temporarily disabled. It is no longer the job of Var # to validate its domain at the time of construction. It only needs to # ensure that whatever object is passed as its domain is suitable for -# interacting with the _VarData interface (e.g., has a bounds method) +# interacting with the VarData interface (e.g., has a bounds method) # The plan is to start adding functionality to the solver interfaces # that will support custom domains. diff --git a/pyomo/dae/misc.py b/pyomo/dae/misc.py index 3e09a055577..dcb73f60c9e 100644 --- a/pyomo/dae/misc.py +++ b/pyomo/dae/misc.py @@ -263,7 +263,7 @@ def _update_var(v): # Note: This is not required it is handled by the _default method on # Var (which is now a IndexedComponent). However, it # would be much slower to rely on that method to generate new - # _VarData for a large number of new indices. + # VarData for a large number of new indices. new_indices = set(v.index_set()) - set(v._data.keys()) for index in new_indices: v.add(index) diff --git a/pyomo/repn/plugins/ampl/ampl_.py b/pyomo/repn/plugins/ampl/ampl_.py index 840bee2166c..1cff45b30c1 100644 --- a/pyomo/repn/plugins/ampl/ampl_.py +++ b/pyomo/repn/plugins/ampl/ampl_.py @@ -168,8 +168,8 @@ def _build_op_template(): _op_template[EXPR.EqualityExpression] = "o24{C}\n" _op_comment[EXPR.EqualityExpression] = "\t#eq" - _op_template[var._VarData] = "v%d{C}\n" - _op_comment[var._VarData] = "\t#%s" + _op_template[var.VarData] = "v%d{C}\n" + _op_comment[var.VarData] = "\t#%s" _op_template[param.ParamData] = "n%r{C}\n" _op_comment[param.ParamData] = "" @@ -733,16 +733,16 @@ def _print_nonlinear_terms_NL(self, exp): % (exp_type) ) - elif isinstance(exp, (var._VarData, IVariable)) and (not exp.is_fixed()): + elif isinstance(exp, (var.VarData, IVariable)) and (not exp.is_fixed()): # (self._output_fixed_variable_bounds or if not self._symbolic_solver_labels: OUTPUT.write( - self._op_string[var._VarData] + self._op_string[var.VarData] % (self.ampl_var_id[self._varID_map[id(exp)]]) ) else: OUTPUT.write( - self._op_string[var._VarData] + self._op_string[var.VarData] % ( self.ampl_var_id[self._varID_map[id(exp)]], self._name_labeler(exp), diff --git a/pyomo/repn/plugins/cpxlp.py b/pyomo/repn/plugins/cpxlp.py index 6228e7c7286..45f4279f8fe 100644 --- a/pyomo/repn/plugins/cpxlp.py +++ b/pyomo/repn/plugins/cpxlp.py @@ -60,7 +60,7 @@ def __init__(self): # The LP writer tracks which variables are # referenced in constraints, so that a user does not end up with a # zillion "unreferenced variables" warning messages. - # This dictionary maps id(_VarData) -> _VarData. + # This dictionary maps id(VarData) -> VarData. self._referenced_variable_ids = {} # Per ticket #4319, we are using %.17g, which mocks the diff --git a/pyomo/repn/plugins/mps.py b/pyomo/repn/plugins/mps.py index ba26783eea1..e1a0d2187fc 100644 --- a/pyomo/repn/plugins/mps.py +++ b/pyomo/repn/plugins/mps.py @@ -62,7 +62,7 @@ def __init__(self, int_marker=False): # referenced in constraints, so that one doesn't end up with a # zillion "unreferenced variables" warning messages. stored at # the object level to avoid additional method arguments. - # dictionary of id(_VarData)->_VarData. + # dictionary of id(VarData)->VarData. self._referenced_variable_ids = {} # Keven Hunter made a nice point about using %.16g in his attachment diff --git a/pyomo/repn/plugins/nl_writer.py b/pyomo/repn/plugins/nl_writer.py index 1a49238f35b..e1691e75f2f 100644 --- a/pyomo/repn/plugins/nl_writer.py +++ b/pyomo/repn/plugins/nl_writer.py @@ -77,7 +77,7 @@ ObjectiveData, ) from pyomo.core.base.suffix import SuffixFinder -from pyomo.core.base.var import _VarData +from pyomo.core.base.var import VarData import pyomo.core.kernel as kernel from pyomo.core.pyomoobject import PyomoObject from pyomo.opt import WriterFactory @@ -129,7 +129,7 @@ class NLWriterInfo(object): Attributes ---------- - variables: List[_VarData] + variables: List[VarData] The list of (unfixed) Pyomo model variables in the order written to the NL file @@ -162,10 +162,10 @@ class NLWriterInfo(object): file in the same order as the :py:attr:`variables` and generated .col file. - eliminated_vars: List[Tuple[_VarData, NumericExpression]] + eliminated_vars: List[Tuple[VarData, NumericExpression]] The list of variables in the model that were eliminated by the - presolve. Each entry is a 2-tuple of (:py:class:`_VarData`, + presolve. Each entry is a 2-tuple of (:py:class:`VarData`, :py:class`NumericExpression`|`float`). The list is in the necessary order for correct evaluation (i.e., all variables appearing in the expression must either have been sent to the @@ -466,7 +466,7 @@ def compile(self, column_order, row_order, obj_order, model_id): self.obj[obj_order[_id]] = val elif _id == model_id: self.prob[0] = val - elif isinstance(obj, (_VarData, ConstraintData, ObjectiveData)): + elif isinstance(obj, (VarData, ConstraintData, ObjectiveData)): missing_component_data.add(obj) elif isinstance(obj, (Var, Constraint, Objective)): # Expand this indexed component to store the diff --git a/pyomo/repn/plugins/standard_form.py b/pyomo/repn/plugins/standard_form.py index e6dc217acc9..434a9b8f35a 100644 --- a/pyomo/repn/plugins/standard_form.py +++ b/pyomo/repn/plugins/standard_form.py @@ -84,17 +84,17 @@ class LinearStandardFormInfo(object): +/- 1 indicating if the row was multiplied by -1 (corresponding to a constraint lower bound) or +1 (upper bound). - columns : List[_VarData] + columns : List[VarData] The list of Pyomo variable objects corresponding to columns in the `A` and `c` matrices. - eliminated_vars: List[Tuple[_VarData, NumericExpression]] + eliminated_vars: List[Tuple[VarData, NumericExpression]] The list of variables from the original model that do not appear in the standard form (usually because they were replaced by nonnegative variables). Each entry is a 2-tuple of - (:py:class:`_VarData`, :py:class`NumericExpression`|`float`). + (:py:class:`VarData`, :py:class`NumericExpression`|`float`). The list is in the necessary order for correct evaluation (i.e., all variables appearing in the expression must either have appeared in the standard form, or appear *earlier* in this list. diff --git a/pyomo/solvers/plugins/solvers/cplex_persistent.py b/pyomo/solvers/plugins/solvers/cplex_persistent.py index fd396a8c87f..754dadc09e2 100644 --- a/pyomo/solvers/plugins/solvers/cplex_persistent.py +++ b/pyomo/solvers/plugins/solvers/cplex_persistent.py @@ -82,7 +82,7 @@ def update_var(self, var): Parameters ---------- - var: Var (scalar Var or single _VarData) + var: Var (scalar Var or single VarData) """ # see PR #366 for discussion about handling indexed @@ -130,7 +130,7 @@ def _add_column(self, var, obj_coef, constraints, coefficients): Parameters ---------- - var: Var (scalar Var or single _VarData) + var: Var (scalar Var or single VarData) obj_coef: float constraints: list of solver constraints coefficients: list of coefficients to put on var in the associated constraint diff --git a/pyomo/solvers/plugins/solvers/gurobi_persistent.py b/pyomo/solvers/plugins/solvers/gurobi_persistent.py index 585a78e3ef1..97a3533c3f9 100644 --- a/pyomo/solvers/plugins/solvers/gurobi_persistent.py +++ b/pyomo/solvers/plugins/solvers/gurobi_persistent.py @@ -111,7 +111,7 @@ def update_var(self, var): Parameters ---------- - var: Var (scalar Var or single _VarData) + var: Var (scalar Var or single VarData) """ # see PR #366 for discussion about handling indexed @@ -710,7 +710,7 @@ def _add_column(self, var, obj_coef, constraints, coefficients): Parameters ---------- - var: Var (scalar Var or single _VarData) + var: Var (scalar Var or single VarData) obj_coef: float constraints: list of solver constraints coefficients: list of coefficients to put on var in the associated constraint diff --git a/pyomo/solvers/plugins/solvers/mosek_persistent.py b/pyomo/solvers/plugins/solvers/mosek_persistent.py index 9e7f8de1b41..efcbb7dd9dd 100644 --- a/pyomo/solvers/plugins/solvers/mosek_persistent.py +++ b/pyomo/solvers/plugins/solvers/mosek_persistent.py @@ -95,7 +95,7 @@ def remove_var(self, solver_var): This will keep any other model components intact. Parameters ---------- - solver_var: Var (scalar Var or single _VarData) + solver_var: Var (scalar Var or single VarData) """ self.remove_vars(solver_var) @@ -106,7 +106,7 @@ def remove_vars(self, *solver_vars): This will keep any other model components intact. Parameters ---------- - *solver_var: Var (scalar Var or single _VarData) + *solver_var: Var (scalar Var or single VarData) """ try: var_ids = [] diff --git a/pyomo/solvers/plugins/solvers/persistent_solver.py b/pyomo/solvers/plugins/solvers/persistent_solver.py index 79cd669dd71..3c2a9e52eab 100644 --- a/pyomo/solvers/plugins/solvers/persistent_solver.py +++ b/pyomo/solvers/plugins/solvers/persistent_solver.py @@ -206,7 +206,7 @@ def add_column(self, model, var, obj_coef, constraints, coefficients): Parameters ---------- model: pyomo ConcreteModel to which the column will be added - var: Var (scalar Var or single _VarData) + var: Var (scalar Var or single VarData) obj_coef: float, pyo.Param constraints: list of scalar Constraints of single ConstraintDatas coefficients: list of the coefficient to put on var in the associated constraint @@ -380,7 +380,7 @@ def remove_var(self, var): Parameters ---------- - var: Var (scalar Var or single _VarData) + var: Var (scalar Var or single VarData) """ # see PR #366 for discussion about handling indexed diff --git a/pyomo/solvers/plugins/solvers/xpress_persistent.py b/pyomo/solvers/plugins/solvers/xpress_persistent.py index 513a7fbc257..fbdc2866dcf 100644 --- a/pyomo/solvers/plugins/solvers/xpress_persistent.py +++ b/pyomo/solvers/plugins/solvers/xpress_persistent.py @@ -90,7 +90,7 @@ def update_var(self, var): Parameters ---------- - var: Var (scalar Var or single _VarData) + var: Var (scalar Var or single VarData) """ # see PR #366 for discussion about handling indexed @@ -124,7 +124,7 @@ def _add_column(self, var, obj_coef, constraints, coefficients): Parameters ---------- - var: Var (scalar Var or single _VarData) + var: Var (scalar Var or single VarData) obj_coef: float constraints: list of solver constraints coefficients: list of coefficients to put on var in the associated constraint diff --git a/pyomo/util/calc_var_value.py b/pyomo/util/calc_var_value.py index d5bceb5c67b..254b82c59cd 100644 --- a/pyomo/util/calc_var_value.py +++ b/pyomo/util/calc_var_value.py @@ -53,7 +53,7 @@ def calculate_variable_from_constraint( Parameters: ----------- - variable: :py:class:`_VarData` + variable: :py:class:`VarData` The variable to solve for constraint: :py:class:`ConstraintData` or relational expression or `tuple` The equality constraint to use to solve for the variable value. From 0e994faacb398642756fdd12cf0802a49cf92dc4 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 18:06:48 -0600 Subject: [PATCH 31/83] Revert "Renamed _SuffixData -> SuffixData" This reverts commit 430f98207353b1e1e7383504aa0336bc852aeb9c. --- pyomo/core/base/suffix.py | 4 ++-- pyomo/repn/plugins/nl_writer.py | 15 +++++---------- 2 files changed, 7 insertions(+), 12 deletions(-) diff --git a/pyomo/core/base/suffix.py b/pyomo/core/base/suffix.py index c4b37789773..be2f732650d 100644 --- a/pyomo/core/base/suffix.py +++ b/pyomo/core/base/suffix.py @@ -129,7 +129,7 @@ class SuffixDirection(enum.IntEnum): IMPORT_EXPORT = 3 -SuffixDataTypeDomain = In(SuffixDataType) +_SuffixDataTypeDomain = In(SuffixDataType) _SuffixDirectionDomain = In(SuffixDirection) @@ -253,7 +253,7 @@ def datatype(self): def datatype(self, datatype): """Set the suffix datatype.""" if datatype is not None: - datatype = SuffixDataTypeDomain(datatype) + datatype = _SuffixDataTypeDomain(datatype) self._datatype = datatype @property diff --git a/pyomo/repn/plugins/nl_writer.py b/pyomo/repn/plugins/nl_writer.py index e1691e75f2f..23e14104b89 100644 --- a/pyomo/repn/plugins/nl_writer.py +++ b/pyomo/repn/plugins/nl_writer.py @@ -423,7 +423,7 @@ def _generate_symbol_map(self, info): return symbol_map -class SuffixData(object): +class _SuffixData(object): def __init__(self, name): self.name = name self.obj = {} @@ -505,11 +505,6 @@ def compile(self, column_order, row_order, obj_order, model_id): ) -class _SuffixData(metaclass=RenamedClass): - __renamed__new_class__ = SuffixData - __renamed__version__ = '6.7.2.dev0' - - class CachingNumericSuffixFinder(SuffixFinder): scale = True @@ -642,7 +637,7 @@ def write(self, model): continue name = suffix.local_name if name not in suffix_data: - suffix_data[name] = SuffixData(name) + suffix_data[name] = _SuffixData(name) suffix_data[name].update(suffix) # # Data structures to support variable/constraint scaling @@ -999,7 +994,7 @@ def write(self, model): "model. To avoid this error please use only one of " "these methods to define special ordered sets." ) - suffix_data[name] = SuffixData(name) + suffix_data[name] = _SuffixData(name) suffix_data[name].datatype.add(Suffix.INT) sos_id = 0 sosno = suffix_data['sosno'] @@ -1349,7 +1344,7 @@ def write(self, model): if not _vals: continue ostream.write(f"S{_field|_float} {len(_vals)} {name}\n") - # Note: SuffixData.compile() guarantees the value is int/float + # Note: _SuffixData.compile() guarantees the value is int/float ostream.write( ''.join(f"{_id} {_vals[_id]!r}\n" for _id in sorted(_vals)) ) @@ -1459,7 +1454,7 @@ def write(self, model): logger.warning("ignoring 'dual' suffix for Model") if data.con: ostream.write(f"d{len(data.con)}\n") - # Note: SuffixData.compile() guarantees the value is int/float + # Note: _SuffixData.compile() guarantees the value is int/float ostream.write( ''.join(f"{_id} {data.con[_id]!r}\n" for _id in sorted(data.con)) ) From b1a7b30cecf901ce0e1c4a9c146814b250e4cc75 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 19:44:54 -0600 Subject: [PATCH 32/83] Update ComponentData imports, provide deprecation paths --- pyomo/core/base/__init__.py | 110 +++++++++++++++++++++-------------- pyomo/core/base/piecewise.py | 2 +- pyomo/core/base/sets.py | 2 +- pyomo/gdp/__init__.py | 8 ++- 4 files changed, 75 insertions(+), 47 deletions(-) diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 0363380af1f..9a06a3e02bb 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -33,10 +33,14 @@ BooleanValue, native_logical_values, ) + from pyomo.core.kernel.objective import minimize, maximize -from pyomo.core.base.config import PyomoOptions -from pyomo.core.base.expression import Expression, ExpressionData +from pyomo.core.base.component import name, Component, ModelComponentFactory +from pyomo.core.base.componentuid import ComponentUID +from pyomo.core.base.config import PyomoOptions +from pyomo.core.base.enums import SortComponents, TraversalStrategy +from pyomo.core.base.instance2dat import instance2dat from pyomo.core.base.label import ( CuidLabeler, CounterLabeler, @@ -47,17 +51,37 @@ NameLabeler, ShortNameLabeler, ) +from pyomo.core.base.misc import display +from pyomo.core.base.reference import Reference +from pyomo.core.base.symbol_map import symbol_map_from_instance +from pyomo.core.base.transformation import ( + Transformation, + TransformationFactory, + ReverseTransformationToken, +) + +from pyomo.core.base.PyomoModel import ( + global_option, + ModelSolution, + ModelSolutions, + Model, + ConcreteModel, + AbstractModel, +) # # Components # -from pyomo.core.base.component import name, Component, ModelComponentFactory -from pyomo.core.base.componentuid import ComponentUID from pyomo.core.base.action import BuildAction -from pyomo.core.base.check import BuildCheck -from pyomo.core.base.set import Set, SetOf, simple_set_rule, RangeSet -from pyomo.core.base.param import Param -from pyomo.core.base.var import Var, VarData, GeneralVarData, ScalarVar, VarList +from pyomo.core.base.block import ( + Block, + BlockData, + ScalarBlock, + active_components, + components, + active_components_data, + components_data, +) from pyomo.core.base.boolean_var import ( BooleanVar, BooleanVarData, @@ -65,6 +89,8 @@ BooleanVarList, ScalarBooleanVar, ) +from pyomo.core.base.check import BuildCheck +from pyomo.core.base.connector import Connector, ConnectorData from pyomo.core.base.constraint import ( simple_constraint_rule, simple_constraintlist_rule, @@ -72,6 +98,8 @@ Constraint, ConstraintData, ) +from pyomo.core.base.expression import Expression, ExpressionData +from pyomo.core.base.external import ExternalFunction from pyomo.core.base.logical_constraint import ( LogicalConstraint, LogicalConstraintList, @@ -84,19 +112,13 @@ ObjectiveList, ObjectiveData, ) -from pyomo.core.base.connector import Connector -from pyomo.core.base.sos import SOSConstraint -from pyomo.core.base.piecewise import Piecewise -from pyomo.core.base.suffix import ( - active_export_suffix_generator, - active_import_suffix_generator, - Suffix, -) -from pyomo.core.base.external import ExternalFunction -from pyomo.core.base.symbol_map import symbol_map_from_instance -from pyomo.core.base.reference import Reference - +from pyomo.core.base.param import Param, ParamData +from pyomo.core.base.piecewise import Piecewise, PiecewiseData from pyomo.core.base.set import ( + Set, + SetData, + SetOf, + RangeSet, Reals, PositiveReals, NonPositiveReals, @@ -116,34 +138,19 @@ PercentFraction, RealInterval, IntegerInterval, + simple_set_rule, ) -from pyomo.core.base.misc import display -from pyomo.core.base.block import ( - Block, - ScalarBlock, - active_components, - components, - active_components_data, - components_data, -) -from pyomo.core.base.enums import SortComponents, TraversalStrategy -from pyomo.core.base.PyomoModel import ( - global_option, - ModelSolution, - ModelSolutions, - Model, - ConcreteModel, - AbstractModel, -) -from pyomo.core.base.transformation import ( - Transformation, - TransformationFactory, - ReverseTransformationToken, +from pyomo.core.base.sos import SOSConstraint, SOSConstraintData +from pyomo.core.base.suffix import ( + active_export_suffix_generator, + active_import_suffix_generator, + Suffix, ) +from pyomo.core.base.var import Var, VarData, GeneralVarData, ScalarVar, VarList -from pyomo.core.base.instance2dat import instance2dat - +# # These APIs are deprecated and should be removed in the near future +# from pyomo.core.base.set import set_options, RealSet, IntegerSet, BooleanSet from pyomo.common.deprecation import relocated_module_attribute @@ -155,4 +162,19 @@ relocated_module_attribute( 'SimpleBooleanVar', 'pyomo.core.base.boolean_var.SimpleBooleanVar', version='6.0' ) +# Historically, only a subset of "private" component data classes were imported here +for _cdata in ( + 'ConstraintData', + 'LogicalConstraintData', + 'ExpressionData', + 'VarData', + 'GeneralVarData', + 'GeneralBooleanVarData', + 'BooleanVarData', + 'ObjectiveData', +): + relocated_module_attribute( + f'_{_cdata}', f'pyomo.core.base.{_cdata}', version='6.7.2.dev0' + ) +del _cdata del relocated_module_attribute diff --git a/pyomo/core/base/piecewise.py b/pyomo/core/base/piecewise.py index f061ebfbdc8..efe500dbfb1 100644 --- a/pyomo/core/base/piecewise.py +++ b/pyomo/core/base/piecewise.py @@ -40,7 +40,7 @@ import enum from pyomo.common.log import is_debug_set -from pyomo.common.deprecation import deprecation_warning +from pyomo.common.deprecation import RenamedClass, deprecation_warning from pyomo.common.numeric_types import value from pyomo.common.timing import ConstructionTimer from pyomo.core.base.block import Block, BlockData diff --git a/pyomo/core/base/sets.py b/pyomo/core/base/sets.py index 3ebdc6875d1..72d49479dd3 100644 --- a/pyomo/core/base/sets.py +++ b/pyomo/core/base/sets.py @@ -17,7 +17,7 @@ process_setarg, set_options, simple_set_rule, - SetDataBase, + _SetDataBase, SetData, Set, SetOf, diff --git a/pyomo/gdp/__init__.py b/pyomo/gdp/__init__.py index a18bc03084a..d204369cdba 100644 --- a/pyomo/gdp/__init__.py +++ b/pyomo/gdp/__init__.py @@ -9,7 +9,13 @@ # This software is distributed under the 3-clause BSD License. # ___________________________________________________________________________ -from pyomo.gdp.disjunct import GDP_Error, Disjunct, Disjunction +from pyomo.gdp.disjunct import ( + GDP_Error, + Disjunct, + DisjunctData, + Disjunction, + DisjunctionData, +) # Do not import these files: importing them registers the transformation # plugins with the pyomo script so that they get automatically invoked. From 1e5b54e7a30ee6ad9de1a956bd1f975148c7efd9 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 20:17:28 -0600 Subject: [PATCH 33/83] Mrege GeneralVarData into VarData class --- pyomo/core/base/var.py | 439 +++++++++++++++++------------------------ 1 file changed, 183 insertions(+), 256 deletions(-) diff --git a/pyomo/core/base/var.py b/pyomo/core/base/var.py index 509238e4e6b..b1634b61c44 100644 --- a/pyomo/core/base/var.py +++ b/pyomo/core/base/var.py @@ -85,246 +85,11 @@ 'value', 'stale', 'fixed', + ('__call__', "access property 'value' on"), ) class VarData(ComponentData, NumericValue): - """This class defines the abstract interface for a single variable. - - Note that this "abstract" class is not intended to be directly - instantiated. - - """ - - __slots__ = () - - # - # Interface - # - - def has_lb(self): - """Returns :const:`False` when the lower bound is - :const:`None` or negative infinity""" - return self.lb is not None - - def has_ub(self): - """Returns :const:`False` when the upper bound is - :const:`None` or positive infinity""" - return self.ub is not None - - # TODO: deprecate this? Properties are generally preferred over "set*()" - def setlb(self, val): - """ - Set the lower bound for this variable after validating that - the value is fixed (or None). - """ - self.lower = val - - # TODO: deprecate this? Properties are generally preferred over "set*()" - def setub(self, val): - """ - Set the upper bound for this variable after validating that - the value is fixed (or None). - """ - self.upper = val - - @property - def bounds(self): - """Returns (or set) the tuple (lower bound, upper bound). - - This returns the current (numeric) values of the lower and upper - bounds as a tuple. If there is no bound, returns None (and not - +/-inf) - - """ - return self.lb, self.ub - - @bounds.setter - def bounds(self, val): - self.lower, self.upper = val - - @property - def lb(self): - """Return (or set) the numeric value of the variable lower bound.""" - lb = value(self.lower) - return None if lb == _ninf else lb - - @lb.setter - def lb(self, val): - self.lower = val - - @property - def ub(self): - """Return (or set) the numeric value of the variable upper bound.""" - ub = value(self.upper) - return None if ub == _inf else ub - - @ub.setter - def ub(self, val): - self.upper = val - - def is_integer(self): - """Returns True when the domain is a contiguous integer range.""" - _id = id(self.domain) - if _id in _known_global_real_domains: - return not _known_global_real_domains[_id] - _interval = self.domain.get_interval() - if _interval is None: - return False - # Note: it is not sufficient to just check the step: the - # starting / ending points must be integers (or not specified) - start, stop, step = _interval - return ( - step == 1 - and (start is None or int(start) == start) - and (stop is None or int(stop) == stop) - ) - - def is_binary(self): - """Returns True when the domain is restricted to Binary values.""" - domain = self.domain - if domain is Binary: - return True - if id(domain) in _known_global_real_domains: - return False - return domain.get_interval() == (0, 1, 1) - - def is_continuous(self): - """Returns True when the domain is a continuous real range""" - _id = id(self.domain) - if _id in _known_global_real_domains: - return _known_global_real_domains[_id] - _interval = self.domain.get_interval() - return _interval is not None and _interval[2] == 0 - - def is_fixed(self): - """Returns True if this variable is fixed, otherwise returns False.""" - return self.fixed - - def is_constant(self): - """Returns False because this is not a constant in an expression.""" - return False - - def is_variable_type(self): - """Returns True because this is a variable.""" - return True - - def is_potentially_variable(self): - """Returns True because this is a variable.""" - return True - - def _compute_polynomial_degree(self, result): - """ - If the variable is fixed, it represents a constant - is a polynomial with degree 0. Otherwise, it has - degree 1. This method is used in expressions to - compute polynomial degree. - """ - if self.fixed: - return 0 - return 1 - - def clear(self): - self.value = None - - def __call__(self, exception=True): - """Compute the value of this variable.""" - return self.value - - # - # Abstract Interface - # - - def set_value(self, val, skip_validation=False): - """Set the current variable value.""" - raise NotImplementedError - - @property - def value(self): - """Return (or set) the value for this variable.""" - raise NotImplementedError - - @property - def domain(self): - """Return (or set) the domain for this variable.""" - raise NotImplementedError - - @property - def lower(self): - """Return (or set) an expression for the variable lower bound.""" - raise NotImplementedError - - @property - def upper(self): - """Return (or set) an expression for the variable upper bound.""" - raise NotImplementedError - - @property - def fixed(self): - """Return (or set) the fixed indicator for this variable. - - Alias for :meth:`is_fixed` / :meth:`fix` / :meth:`unfix`. - - """ - raise NotImplementedError - - @property - def stale(self): - """The stale status for this variable. - - Variables are "stale" if their current value was not updated as - part of the most recent model update. A "model update" can be - one of several things: a solver invocation, loading a previous - solution, or manually updating a non-stale :class:`Var` value. - - Returns - ------- - bool - - Notes - ----- - Fixed :class:`Var` objects will be stale after invoking a solver - (as their value was not updated by the solver). - - Updating a stale :class:`Var` value will not cause other - variable values to be come stale. However, updating the first - non-stale :class:`Var` value after a solve or solution load - *will* cause all other variables to be marked as stale - - """ - raise NotImplementedError - - def fix(self, value=NOTSET, skip_validation=False): - """Fix the value of this variable (treat as nonvariable) - - This sets the :attr:`fixed` indicator to True. If ``value`` is - provided, the value (and the ``skip_validation`` flag) are first - passed to :meth:`set_value()`. - - """ - self.fixed = True - if value is not NOTSET: - self.set_value(value, skip_validation) - - def unfix(self): - """Unfix this variable (treat as variable in solver interfaces) - - This sets the :attr:`fixed` indicator to False. - - """ - self.fixed = False - - def free(self): - """Alias for :meth:`unfix`""" - return self.unfix() - - -class _VarData(metaclass=RenamedClass): - __renamed__new_class__ = VarData - __renamed__version__ = '6.7.2.dev0' - - -class GeneralVarData(VarData): """This class defines the data for a single variable.""" __slots__ = ('_value', '_lb', '_ub', '_domain', '_fixed', '_stale') @@ -365,10 +130,6 @@ def copy(cls, src): self._index = src._index return self - # - # Abstract Interface - # - def set_value(self, val, skip_validation=False): """Set the current variable value. @@ -429,14 +190,20 @@ def set_value(self, val, skip_validation=False): @property def value(self): + """Return (or set) the value for this variable.""" return self._value @value.setter def value(self, val): self.set_value(val) + def __call__(self, exception=True): + """Compute the value of this variable.""" + return self._value + @property def domain(self): + """Return (or set) the domain for this variable.""" return self._domain @domain.setter @@ -453,9 +220,42 @@ def domain(self, domain): ) raise - @VarData.bounds.getter + def has_lb(self): + """Returns :const:`False` when the lower bound is + :const:`None` or negative infinity""" + return self.lb is not None + + def has_ub(self): + """Returns :const:`False` when the upper bound is + :const:`None` or positive infinity""" + return self.ub is not None + + # TODO: deprecate this? Properties are generally preferred over "set*()" + def setlb(self, val): + """ + Set the lower bound for this variable after validating that + the value is fixed (or None). + """ + self.lower = val + + # TODO: deprecate this? Properties are generally preferred over "set*()" + def setub(self, val): + """ + Set the upper bound for this variable after validating that + the value is fixed (or None). + """ + self.upper = val + + @property def bounds(self): - # Custom implementation of VarData.bounds to avoid unnecessary + """Returns (or set) the tuple (lower bound, upper bound). + + This returns the current (numeric) values of the lower and upper + bounds as a tuple. If there is no bound, returns None (and not + +/-inf) + + """ + # Custom implementation of lb / ub to avoid unnecessary # expression generation and duplicate calls to domain.bounds() domain_lb, domain_ub = self.domain.bounds() # lb is the tighter of the domain and bounds @@ -496,10 +296,14 @@ def bounds(self): ub = min(ub, domain_ub) return lb, ub - @VarData.lb.getter + @bounds.setter + def bounds(self, val): + self.lower, self.upper = val + + @property def lb(self): - # Custom implementation of VarData.lb to avoid unnecessary - # expression generation + """Return (or set) the numeric value of the variable lower bound.""" + # Note: Implementation avoids unnecessary expression generation domain_lb, domain_ub = self.domain.bounds() # lb is the tighter of the domain and bounds lb = self._lb @@ -521,10 +325,14 @@ def lb(self): lb = max(lb, domain_lb) return lb - @VarData.ub.getter + @lb.setter + def lb(self, val): + self.lower = val + + @property def ub(self): - # Custom implementation of VarData.ub to avoid unnecessary - # expression generation + """Return (or set) the numeric value of the variable upper bound.""" + # Note: implementation avoids unnecessary expression generation domain_lb, domain_ub = self.domain.bounds() # ub is the tighter of the domain and bounds ub = self._ub @@ -546,6 +354,10 @@ def ub(self): ub = min(ub, domain_ub) return ub + @ub.setter + def ub(self, val): + self.upper = val + @property def lower(self): """Return (or set) an expression for the variable lower bound. @@ -602,8 +414,37 @@ def get_units(self): # component if not scalar return self.parent_component()._units + def fix(self, value=NOTSET, skip_validation=False): + """Fix the value of this variable (treat as nonvariable) + + This sets the :attr:`fixed` indicator to True. If ``value`` is + provided, the value (and the ``skip_validation`` flag) are first + passed to :meth:`set_value()`. + + """ + self.fixed = True + if value is not NOTSET: + self.set_value(value, skip_validation) + + def unfix(self): + """Unfix this variable (treat as variable in solver interfaces) + + This sets the :attr:`fixed` indicator to False. + + """ + self.fixed = False + + def free(self): + """Alias for :meth:`unfix`""" + return self.unfix() + @property def fixed(self): + """Return (or set) the fixed indicator for this variable. + + Alias for :meth:`is_fixed` / :meth:`fix` / :meth:`unfix`. + + """ return self._fixed @fixed.setter @@ -612,6 +453,28 @@ def fixed(self, val): @property def stale(self): + """The stale status for this variable. + + Variables are "stale" if their current value was not updated as + part of the most recent model update. A "model update" can be + one of several things: a solver invocation, loading a previous + solution, or manually updating a non-stale :class:`Var` value. + + Returns + ------- + bool + + Notes + ----- + Fixed :class:`Var` objects will be stale after invoking a solver + (as their value was not updated by the solver). + + Updating a stale :class:`Var` value will not cause other + variable values to be come stale. However, updating the first + non-stale :class:`Var` value after a solve or solution load + *will* cause all other variables to be marked as stale + + """ return StaleFlagManager.is_stale(self._stale) @stale.setter @@ -621,11 +484,70 @@ def stale(self, val): else: self._stale = StaleFlagManager.get_flag(0) - # Note: override the base class definition to avoid a call through a - # property + def is_integer(self): + """Returns True when the domain is a contiguous integer range.""" + _id = id(self.domain) + if _id in _known_global_real_domains: + return not _known_global_real_domains[_id] + _interval = self.domain.get_interval() + if _interval is None: + return False + # Note: it is not sufficient to just check the step: the + # starting / ending points must be integers (or not specified) + start, stop, step = _interval + return ( + step == 1 + and (start is None or int(start) == start) + and (stop is None or int(stop) == stop) + ) + + def is_binary(self): + """Returns True when the domain is restricted to Binary values.""" + domain = self.domain + if domain is Binary: + return True + if id(domain) in _known_global_real_domains: + return False + return domain.get_interval() == (0, 1, 1) + + def is_continuous(self): + """Returns True when the domain is a continuous real range""" + _id = id(self.domain) + if _id in _known_global_real_domains: + return _known_global_real_domains[_id] + _interval = self.domain.get_interval() + return _interval is not None and _interval[2] == 0 + def is_fixed(self): + """Returns True if this variable is fixed, otherwise returns False.""" return self._fixed + def is_constant(self): + """Returns False because this is not a constant in an expression.""" + return False + + def is_variable_type(self): + """Returns True because this is a variable.""" + return True + + def is_potentially_variable(self): + """Returns True because this is a variable.""" + return True + + def clear(self): + self.value = None + + def _compute_polynomial_degree(self, result): + """ + If the variable is fixed, it represents a constant + is a polynomial with degree 0. Otherwise, it has + degree 1. This method is used in expressions to + compute polynomial degree. + """ + if self._fixed: + return 0 + return 1 + def _process_bound(self, val, bound_type): if type(val) in native_numeric_types or val is None: # TODO: warn/error: check if this Var has units: assigning @@ -648,8 +570,13 @@ def _process_bound(self, val, bound_type): return val -class _GeneralVarData(metaclass=RenamedClass): - __renamed__new_class__ = GeneralVarData +class _VarData(metaclass=RenamedClass): + __renamed__new_class__ = VarData + __renamed__version__ = '6.7.2.dev0' + + +class _VarData(metaclass=RenamedClass): + __renamed__new_class__ = VarData __renamed__version__ = '6.7.2.dev0' @@ -678,7 +605,7 @@ class Var(IndexedComponent, IndexedComponent_NDArrayMixin): doc (str, optional): Text describing this component. """ - _ComponentDataClass = GeneralVarData + _ComponentDataClass = VarData @overload def __new__(cls: Type[Var], *args, **kwargs) -> Union[ScalarVar, IndexedVar]: ... @@ -962,11 +889,11 @@ def _pprint(self): ) -class ScalarVar(GeneralVarData, Var): +class ScalarVar(VarData, Var): """A single variable.""" def __init__(self, *args, **kwd): - GeneralVarData.__init__(self, component=self) + VarData.__init__(self, component=self) Var.__init__(self, *args, **kwd) self._index = UnindexedComponent_index @@ -1067,7 +994,7 @@ def domain(self, domain): # between potentially variable GetItemExpression objects and # "constant" GetItemExpression objects. That will need to wait for # the expression rework [JDS; Nov 22]. - def __getitem__(self, args) -> GeneralVarData: + def __getitem__(self, args) -> VarData: try: return super().__getitem__(args) except RuntimeError: From cf7ff538df92247af0cd7e7c3e34ed4f4549d8af Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 20:21:36 -0600 Subject: [PATCH 34/83] Update references from GeneralVarData to VarData --- pyomo/contrib/appsi/base.py | 60 +++++++++---------- pyomo/contrib/appsi/cmodel/src/expression.hpp | 6 +- pyomo/contrib/appsi/fbbt.py | 10 ++-- pyomo/contrib/appsi/solvers/cbc.py | 16 ++--- pyomo/contrib/appsi/solvers/cplex.py | 16 ++--- pyomo/contrib/appsi/solvers/gurobi.py | 12 ++-- pyomo/contrib/appsi/solvers/highs.py | 8 +-- pyomo/contrib/appsi/solvers/ipopt.py | 16 ++--- pyomo/contrib/appsi/solvers/wntr.py | 8 +-- pyomo/contrib/appsi/writers/lp_writer.py | 8 +-- pyomo/contrib/appsi/writers/nl_writer.py | 8 +-- pyomo/contrib/cp/repn/docplex_writer.py | 4 +- .../logical_to_disjunctive_walker.py | 4 +- pyomo/contrib/latex_printer/latex_printer.py | 12 ++-- pyomo/contrib/parmest/utils/scenario_tree.py | 2 +- pyomo/contrib/solver/base.py | 24 ++++---- pyomo/contrib/solver/gurobi.py | 12 ++-- pyomo/contrib/solver/ipopt.py | 6 +- pyomo/contrib/solver/persistent.py | 18 +++--- pyomo/contrib/solver/solution.py | 26 ++++---- .../contrib/solver/tests/unit/test_results.py | 10 ++-- .../trustregion/tests/test_interface.py | 4 +- pyomo/core/base/__init__.py | 9 ++- pyomo/core/base/component.py | 2 +- pyomo/core/expr/calculus/derivatives.py | 6 +- pyomo/core/tests/transform/test_add_slacks.py | 2 +- pyomo/core/tests/unit/test_dict_objects.py | 6 +- pyomo/core/tests/unit/test_list_objects.py | 6 +- pyomo/core/tests/unit/test_numeric_expr.py | 4 +- pyomo/core/tests/unit/test_reference.py | 12 ++-- pyomo/repn/standard_repn.py | 6 +- .../plugins/solvers/gurobi_persistent.py | 4 +- pyomo/util/report_scaling.py | 4 +- 33 files changed, 171 insertions(+), 180 deletions(-) diff --git a/pyomo/contrib/appsi/base.py b/pyomo/contrib/appsi/base.py index 409c8e2596c..930ff8393e9 100644 --- a/pyomo/contrib/appsi/base.py +++ b/pyomo/contrib/appsi/base.py @@ -23,7 +23,7 @@ ) from pyomo.core.base.constraint import GeneralConstraintData, Constraint from pyomo.core.base.sos import SOSConstraintData, SOSConstraint -from pyomo.core.base.var import GeneralVarData, Var +from pyomo.core.base.var import VarData, Var from pyomo.core.base.param import ParamData, Param from pyomo.core.base.block import BlockData, Block from pyomo.core.base.objective import GeneralObjectiveData @@ -179,9 +179,7 @@ def __init__( class SolutionLoaderBase(abc.ABC): - def load_vars( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> NoReturn: + def load_vars(self, vars_to_load: Optional[Sequence[VarData]] = None) -> NoReturn: """ Load the solution of the primal variables into the value attribute of the variables. @@ -197,8 +195,8 @@ def load_vars( @abc.abstractmethod def get_primals( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: """ Returns a ComponentMap mapping variable to var value. @@ -256,8 +254,8 @@ def get_slacks( ) def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: """ Returns a ComponentMap mapping variable to reduced cost. @@ -303,8 +301,8 @@ def __init__( self._reduced_costs = reduced_costs def get_primals( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if self._primals is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' @@ -353,8 +351,8 @@ def get_slacks( return slacks def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if self._reduced_costs is None: raise RuntimeError( 'Solution loader does not currently have valid reduced costs. Please ' @@ -708,9 +706,7 @@ class PersistentSolver(Solver): def is_persistent(self): return True - def load_vars( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> NoReturn: + def load_vars(self, vars_to_load: Optional[Sequence[VarData]] = None) -> NoReturn: """ Load the solution of the primal variables into the value attribute of the variables. @@ -726,8 +722,8 @@ def load_vars( @abc.abstractmethod def get_primals( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: pass def get_duals( @@ -771,8 +767,8 @@ def get_slacks( ) def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: """ Parameters ---------- @@ -799,7 +795,7 @@ def set_instance(self, model): pass @abc.abstractmethod - def add_variables(self, variables: List[GeneralVarData]): + def add_variables(self, variables: List[VarData]): pass @abc.abstractmethod @@ -815,7 +811,7 @@ def add_block(self, block: BlockData): pass @abc.abstractmethod - def remove_variables(self, variables: List[GeneralVarData]): + def remove_variables(self, variables: List[VarData]): pass @abc.abstractmethod @@ -835,7 +831,7 @@ def set_objective(self, obj: GeneralObjectiveData): pass @abc.abstractmethod - def update_variables(self, variables: List[GeneralVarData]): + def update_variables(self, variables: List[VarData]): pass @abc.abstractmethod @@ -869,8 +865,8 @@ def get_slacks( return self._solver.get_slacks(cons_to_load=cons_to_load) def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: self._assert_solution_still_valid() return self._solver.get_reduced_costs(vars_to_load=vars_to_load) @@ -954,10 +950,10 @@ def set_instance(self, model): self.set_objective(None) @abc.abstractmethod - def _add_variables(self, variables: List[GeneralVarData]): + def _add_variables(self, variables: List[VarData]): pass - def add_variables(self, variables: List[GeneralVarData]): + def add_variables(self, variables: List[VarData]): for v in variables: if id(v) in self._referenced_variables: raise ValueError( @@ -987,7 +983,7 @@ def add_params(self, params: List[ParamData]): def _add_constraints(self, cons: List[GeneralConstraintData]): pass - def _check_for_new_vars(self, variables: List[GeneralVarData]): + def _check_for_new_vars(self, variables: List[VarData]): new_vars = dict() for v in variables: v_id = id(v) @@ -995,7 +991,7 @@ def _check_for_new_vars(self, variables: List[GeneralVarData]): new_vars[v_id] = v self.add_variables(list(new_vars.values())) - def _check_to_remove_vars(self, variables: List[GeneralVarData]): + def _check_to_remove_vars(self, variables: List[VarData]): vars_to_remove = dict() for v in variables: v_id = id(v) @@ -1174,10 +1170,10 @@ def remove_sos_constraints(self, cons: List[SOSConstraintData]): del self._vars_referenced_by_con[con] @abc.abstractmethod - def _remove_variables(self, variables: List[GeneralVarData]): + def _remove_variables(self, variables: List[VarData]): pass - def remove_variables(self, variables: List[GeneralVarData]): + def remove_variables(self, variables: List[VarData]): self._remove_variables(variables) for v in variables: v_id = id(v) @@ -1246,10 +1242,10 @@ def remove_block(self, block): ) @abc.abstractmethod - def _update_variables(self, variables: List[GeneralVarData]): + def _update_variables(self, variables: List[VarData]): pass - def update_variables(self, variables: List[GeneralVarData]): + def update_variables(self, variables: List[VarData]): for v in variables: self._vars[id(v)] = ( v, diff --git a/pyomo/contrib/appsi/cmodel/src/expression.hpp b/pyomo/contrib/appsi/cmodel/src/expression.hpp index 0c0777ef468..803bb21b6e2 100644 --- a/pyomo/contrib/appsi/cmodel/src/expression.hpp +++ b/pyomo/contrib/appsi/cmodel/src/expression.hpp @@ -680,7 +680,7 @@ class PyomoExprTypes { expr_type_map[np_float32] = py_float; expr_type_map[np_float64] = py_float; expr_type_map[ScalarVar] = var; - expr_type_map[_GeneralVarData] = var; + expr_type_map[_VarData] = var; expr_type_map[AutoLinkedBinaryVar] = var; expr_type_map[ScalarParam] = param; expr_type_map[_ParamData] = param; @@ -732,8 +732,8 @@ class PyomoExprTypes { py::module_::import("pyomo.core.base.param").attr("_ParamData"); py::object ScalarVar = py::module_::import("pyomo.core.base.var").attr("ScalarVar"); - py::object _GeneralVarData = - py::module_::import("pyomo.core.base.var").attr("_GeneralVarData"); + py::object _VarData = + py::module_::import("pyomo.core.base.var").attr("_VarData"); py::object AutoLinkedBinaryVar = py::module_::import("pyomo.gdp.disjunct").attr("AutoLinkedBinaryVar"); py::object numeric_expr = py::module_::import("pyomo.core.expr.numeric_expr"); diff --git a/pyomo/contrib/appsi/fbbt.py b/pyomo/contrib/appsi/fbbt.py index 122ca5f7ffd..1ebb3d40381 100644 --- a/pyomo/contrib/appsi/fbbt.py +++ b/pyomo/contrib/appsi/fbbt.py @@ -18,7 +18,7 @@ ) from .cmodel import cmodel, cmodel_available from typing import List, Optional -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.param import ParamData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import SOSConstraintData @@ -121,7 +121,7 @@ def set_instance(self, model, symbolic_solver_labels: Optional[bool] = None): if self._objective is None: self.set_objective(None) - def _add_variables(self, variables: List[GeneralVarData]): + def _add_variables(self, variables: List[VarData]): if self._symbolic_solver_labels: set_name = True symbol_map = self._symbol_map @@ -190,7 +190,7 @@ def _remove_sos_constraints(self, cons: List[SOSConstraintData]): 'IntervalTightener does not support SOS constraints' ) - def _remove_variables(self, variables: List[GeneralVarData]): + def _remove_variables(self, variables: List[VarData]): if self._symbolic_solver_labels: for v in variables: self._symbol_map.removeSymbol(v) @@ -205,7 +205,7 @@ def _remove_params(self, params: List[ParamData]): for p in params: del self._param_map[id(p)] - def _update_variables(self, variables: List[GeneralVarData]): + def _update_variables(self, variables: List[VarData]): cmodel.process_pyomo_vars( self._pyomo_expr_types, variables, @@ -304,7 +304,7 @@ def perform_fbbt( self._deactivate_satisfied_cons() return n_iter - def perform_fbbt_with_seed(self, model: BlockData, seed_var: GeneralVarData): + def perform_fbbt_with_seed(self, model: BlockData, seed_var: VarData): if model is not self._model: self.set_instance(model) else: diff --git a/pyomo/contrib/appsi/solvers/cbc.py b/pyomo/contrib/appsi/solvers/cbc.py index d03e6e31c54..7db9a32764e 100644 --- a/pyomo/contrib/appsi/solvers/cbc.py +++ b/pyomo/contrib/appsi/solvers/cbc.py @@ -26,7 +26,7 @@ import math from pyomo.common.collections import ComponentMap from typing import Optional, Sequence, NoReturn, List, Mapping -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import ParamData @@ -164,7 +164,7 @@ def symbol_map(self): def set_instance(self, model): self._writer.set_instance(model) - def add_variables(self, variables: List[GeneralVarData]): + def add_variables(self, variables: List[VarData]): self._writer.add_variables(variables) def add_params(self, params: List[ParamData]): @@ -176,7 +176,7 @@ def add_constraints(self, cons: List[GeneralConstraintData]): def add_block(self, block: BlockData): self._writer.add_block(block) - def remove_variables(self, variables: List[GeneralVarData]): + def remove_variables(self, variables: List[VarData]): self._writer.remove_variables(variables) def remove_params(self, params: List[ParamData]): @@ -191,7 +191,7 @@ def remove_block(self, block: BlockData): def set_objective(self, obj: GeneralObjectiveData): self._writer.set_objective(obj) - def update_variables(self, variables: List[GeneralVarData]): + def update_variables(self, variables: List[VarData]): self._writer.update_variables(variables) def update_params(self): @@ -440,8 +440,8 @@ def _check_and_escape_options(): return results def get_primals( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if ( self._last_results_object is None or self._last_results_object.best_feasible_objective is None @@ -477,8 +477,8 @@ def get_duals(self, cons_to_load=None): return {c: self._dual_sol[c] for c in cons_to_load} def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if ( self._last_results_object is None or self._last_results_object.termination_condition diff --git a/pyomo/contrib/appsi/solvers/cplex.py b/pyomo/contrib/appsi/solvers/cplex.py index 55259244d45..0ed3495ac1c 100644 --- a/pyomo/contrib/appsi/solvers/cplex.py +++ b/pyomo/contrib/appsi/solvers/cplex.py @@ -22,7 +22,7 @@ import math from pyomo.common.collections import ComponentMap from typing import Optional, Sequence, NoReturn, List, Mapping, Dict -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import ParamData @@ -179,7 +179,7 @@ def update_config(self): def set_instance(self, model): self._writer.set_instance(model) - def add_variables(self, variables: List[GeneralVarData]): + def add_variables(self, variables: List[VarData]): self._writer.add_variables(variables) def add_params(self, params: List[ParamData]): @@ -191,7 +191,7 @@ def add_constraints(self, cons: List[GeneralConstraintData]): def add_block(self, block: BlockData): self._writer.add_block(block) - def remove_variables(self, variables: List[GeneralVarData]): + def remove_variables(self, variables: List[VarData]): self._writer.remove_variables(variables) def remove_params(self, params: List[ParamData]): @@ -206,7 +206,7 @@ def remove_block(self, block: BlockData): def set_objective(self, obj: GeneralObjectiveData): self._writer.set_objective(obj) - def update_variables(self, variables: List[GeneralVarData]): + def update_variables(self, variables: List[VarData]): self._writer.update_variables(variables) def update_params(self): @@ -362,8 +362,8 @@ def _postsolve(self, timer: HierarchicalTimer, solve_time): return results def get_primals( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if ( self._cplex_model.solution.get_solution_type() == self._cplex_model.solution.type.none @@ -440,8 +440,8 @@ def get_duals( return res def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if ( self._cplex_model.solution.get_solution_type() == self._cplex_model.solution.type.none diff --git a/pyomo/contrib/appsi/solvers/gurobi.py b/pyomo/contrib/appsi/solvers/gurobi.py index 8606d44cd46..e2ecd9b69e7 100644 --- a/pyomo/contrib/appsi/solvers/gurobi.py +++ b/pyomo/contrib/appsi/solvers/gurobi.py @@ -23,7 +23,7 @@ from pyomo.common.config import ConfigValue, NonNegativeInt from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler -from pyomo.core.base.var import Var, GeneralVarData +from pyomo.core.base.var import Var, VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.param import ParamData @@ -458,7 +458,7 @@ def _process_domain_and_bounds( return lb, ub, vtype - def _add_variables(self, variables: List[GeneralVarData]): + def _add_variables(self, variables: List[VarData]): var_names = list() vtypes = list() lbs = list() @@ -759,7 +759,7 @@ def _remove_sos_constraints(self, cons: List[SOSConstraintData]): del self._pyomo_sos_to_solver_sos_map[con] self._needs_updated = True - def _remove_variables(self, variables: List[GeneralVarData]): + def _remove_variables(self, variables: List[VarData]): for var in variables: v_id = id(var) if var in self._vars_added_since_update: @@ -774,7 +774,7 @@ def _remove_variables(self, variables: List[GeneralVarData]): def _remove_params(self, params: List[ParamData]): pass - def _update_variables(self, variables: List[GeneralVarData]): + def _update_variables(self, variables: List[VarData]): for var in variables: var_id = id(var) if var_id not in self._pyomo_var_to_solver_var_map: @@ -1221,7 +1221,7 @@ def set_var_attr(self, var, attr, val): Parameters ---------- - var: pyomo.core.base.var.GeneralVarData + var: pyomo.core.base.var.VarData The pyomo var for which the corresponding gurobi var attribute should be modified. attr: str @@ -1256,7 +1256,7 @@ def get_var_attr(self, var, attr): Parameters ---------- - var: pyomo.core.base.var.GeneralVarData + var: pyomo.core.base.var.VarData The pyomo var for which the corresponding gurobi var attribute should be retrieved. attr: str diff --git a/pyomo/contrib/appsi/solvers/highs.py b/pyomo/contrib/appsi/solvers/highs.py index 5af7b297684..c3083ac78d3 100644 --- a/pyomo/contrib/appsi/solvers/highs.py +++ b/pyomo/contrib/appsi/solvers/highs.py @@ -20,7 +20,7 @@ from pyomo.common.log import LogStream from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.param import ParamData @@ -308,7 +308,7 @@ def _process_domain_and_bounds(self, var_id): return lb, ub, vtype - def _add_variables(self, variables: List[GeneralVarData]): + def _add_variables(self, variables: List[VarData]): self._sol = None if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() @@ -493,7 +493,7 @@ def _remove_sos_constraints(self, cons: List[SOSConstraintData]): 'Highs interface does not support SOS constraints' ) - def _remove_variables(self, variables: List[GeneralVarData]): + def _remove_variables(self, variables: List[VarData]): self._sol = None if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() @@ -518,7 +518,7 @@ def _remove_variables(self, variables: List[GeneralVarData]): def _remove_params(self, params: List[ParamData]): pass - def _update_variables(self, variables: List[GeneralVarData]): + def _update_variables(self, variables: List[VarData]): self._sol = None if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() diff --git a/pyomo/contrib/appsi/solvers/ipopt.py b/pyomo/contrib/appsi/solvers/ipopt.py index ca75a1b02c8..5cd9a51785d 100644 --- a/pyomo/contrib/appsi/solvers/ipopt.py +++ b/pyomo/contrib/appsi/solvers/ipopt.py @@ -28,7 +28,7 @@ from pyomo.core.expr.numvalue import value from pyomo.core.expr.visitor import replace_expressions from typing import Optional, Sequence, NoReturn, List, Mapping -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import ParamData @@ -228,7 +228,7 @@ def set_instance(self, model): self._writer.config.symbolic_solver_labels = self.config.symbolic_solver_labels self._writer.set_instance(model) - def add_variables(self, variables: List[GeneralVarData]): + def add_variables(self, variables: List[VarData]): self._writer.add_variables(variables) def add_params(self, params: List[ParamData]): @@ -240,7 +240,7 @@ def add_constraints(self, cons: List[GeneralConstraintData]): def add_block(self, block: BlockData): self._writer.add_block(block) - def remove_variables(self, variables: List[GeneralVarData]): + def remove_variables(self, variables: List[VarData]): self._writer.remove_variables(variables) def remove_params(self, params: List[ParamData]): @@ -255,7 +255,7 @@ def remove_block(self, block: BlockData): def set_objective(self, obj: GeneralObjectiveData): self._writer.set_objective(obj) - def update_variables(self, variables: List[GeneralVarData]): + def update_variables(self, variables: List[VarData]): self._writer.update_variables(variables) def update_params(self): @@ -514,8 +514,8 @@ def _apply_solver(self, timer: HierarchicalTimer): return results def get_primals( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if ( self._last_results_object is None or self._last_results_object.best_feasible_objective is None @@ -551,8 +551,8 @@ def get_duals(self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = No return {c: self._dual_sol[c] for c in cons_to_load} def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if ( self._last_results_object is None or self._last_results_object.termination_condition diff --git a/pyomo/contrib/appsi/solvers/wntr.py b/pyomo/contrib/appsi/solvers/wntr.py index 8f2650dabb6..62c4b0ed358 100644 --- a/pyomo/contrib/appsi/solvers/wntr.py +++ b/pyomo/contrib/appsi/solvers/wntr.py @@ -40,7 +40,7 @@ from pyomo.core.expr.numvalue import native_numeric_types from typing import Dict, Optional, List from pyomo.core.base.block import BlockData -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.param import ParamData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.common.timing import HierarchicalTimer @@ -239,7 +239,7 @@ def set_instance(self, model): self.add_block(model) - def _add_variables(self, variables: List[GeneralVarData]): + def _add_variables(self, variables: List[VarData]): aml = wntr.sim.aml.aml for var in variables: varname = self._symbol_map.getSymbol(var, self._labeler) @@ -302,7 +302,7 @@ def _remove_constraints(self, cons: List[GeneralConstraintData]): del self._pyomo_con_to_solver_con_map[con] self._needs_updated = True - def _remove_variables(self, variables: List[GeneralVarData]): + def _remove_variables(self, variables: List[VarData]): for var in variables: v_id = id(var) solver_var = self._pyomo_var_to_solver_var_map[v_id] @@ -322,7 +322,7 @@ def _remove_params(self, params: List[ParamData]): self._symbol_map.removeSymbol(p) del self._pyomo_param_to_solver_param_map[p_id] - def _update_variables(self, variables: List[GeneralVarData]): + def _update_variables(self, variables: List[VarData]): aml = wntr.sim.aml.aml for var in variables: v_id = id(var) diff --git a/pyomo/contrib/appsi/writers/lp_writer.py b/pyomo/contrib/appsi/writers/lp_writer.py index 3a6682d5c00..4be2b32d83d 100644 --- a/pyomo/contrib/appsi/writers/lp_writer.py +++ b/pyomo/contrib/appsi/writers/lp_writer.py @@ -11,7 +11,7 @@ from typing import List from pyomo.core.base.param import ParamData -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.sos import SOSConstraintData @@ -77,7 +77,7 @@ def set_instance(self, model): if self._objective is None: self.set_objective(None) - def _add_variables(self, variables: List[GeneralVarData]): + def _add_variables(self, variables: List[VarData]): cmodel.process_pyomo_vars( self._expr_types, variables, @@ -117,7 +117,7 @@ def _remove_sos_constraints(self, cons: List[SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('LP writer does not yet support SOS constraints') - def _remove_variables(self, variables: List[GeneralVarData]): + def _remove_variables(self, variables: List[VarData]): for v in variables: cvar = self._pyomo_var_to_solver_var_map.pop(id(v)) del self._solver_var_to_pyomo_var_map[cvar] @@ -128,7 +128,7 @@ def _remove_params(self, params: List[ParamData]): del self._pyomo_param_to_solver_param_map[id(p)] self._symbol_map.removeSymbol(p) - def _update_variables(self, variables: List[GeneralVarData]): + def _update_variables(self, variables: List[VarData]): cmodel.process_pyomo_vars( self._expr_types, variables, diff --git a/pyomo/contrib/appsi/writers/nl_writer.py b/pyomo/contrib/appsi/writers/nl_writer.py index c46cb1c0723..70176146a1e 100644 --- a/pyomo/contrib/appsi/writers/nl_writer.py +++ b/pyomo/contrib/appsi/writers/nl_writer.py @@ -11,7 +11,7 @@ from typing import List from pyomo.core.base.param import ParamData -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.sos import SOSConstraintData @@ -78,7 +78,7 @@ def set_instance(self, model): self.set_objective(None) self._set_pyomo_amplfunc_env() - def _add_variables(self, variables: List[GeneralVarData]): + def _add_variables(self, variables: List[VarData]): if self.config.symbolic_solver_labels: set_name = True symbol_map = self._symbol_map @@ -144,7 +144,7 @@ def _remove_sos_constraints(self, cons: List[SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('NL writer does not support SOS constraints') - def _remove_variables(self, variables: List[GeneralVarData]): + def _remove_variables(self, variables: List[VarData]): if self.config.symbolic_solver_labels: for v in variables: self._symbol_map.removeSymbol(v) @@ -161,7 +161,7 @@ def _remove_params(self, params: List[ParamData]): for p in params: del self._pyomo_param_to_solver_param_map[id(p)] - def _update_variables(self, variables: List[GeneralVarData]): + def _update_variables(self, variables: List[VarData]): cmodel.process_pyomo_vars( self._expr_types, variables, diff --git a/pyomo/contrib/cp/repn/docplex_writer.py b/pyomo/contrib/cp/repn/docplex_writer.py index 75095755895..221fd61af5b 100644 --- a/pyomo/contrib/cp/repn/docplex_writer.py +++ b/pyomo/contrib/cp/repn/docplex_writer.py @@ -65,7 +65,7 @@ ) from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.param import IndexedParam, ScalarParam, ParamData -from pyomo.core.base.var import ScalarVar, GeneralVarData, IndexedVar +from pyomo.core.base.var import ScalarVar, VarData, IndexedVar import pyomo.core.expr as EXPR from pyomo.core.expr.visitor import StreamBasedExpressionVisitor, identify_variables from pyomo.core.base import Set, RangeSet @@ -961,7 +961,7 @@ class LogicalToDoCplex(StreamBasedExpressionVisitor): IntervalVarData: _before_interval_var, IndexedIntervalVar: _before_indexed_interval_var, ScalarVar: _before_var, - GeneralVarData: _before_var, + VarData: _before_var, IndexedVar: _before_indexed_var, ScalarBooleanVar: _before_boolean_var, GeneralBooleanVarData: _before_boolean_var, diff --git a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py index a228b1561dd..d9483c0ed14 100644 --- a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py +++ b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py @@ -29,7 +29,7 @@ import pyomo.core.base.boolean_var as BV from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.param import ScalarParam, ParamData -from pyomo.core.base.var import ScalarVar, GeneralVarData +from pyomo.core.base.var import ScalarVar, VarData from pyomo.gdp.disjunct import AutoLinkedBooleanVar, Disjunct, Disjunction @@ -216,7 +216,7 @@ def _dispatch_atmost(visitor, node, *args): # for the moment, these are all just so we can get good error messages when we # don't handle them: _before_child_dispatcher[ScalarVar] = _dispatch_var -_before_child_dispatcher[GeneralVarData] = _dispatch_var +_before_child_dispatcher[VarData] = _dispatch_var _before_child_dispatcher[GeneralExpressionData] = _dispatch_expression _before_child_dispatcher[ScalarExpression] = _dispatch_expression diff --git a/pyomo/contrib/latex_printer/latex_printer.py b/pyomo/contrib/latex_printer/latex_printer.py index 28d1ca52943..e11543cb375 100644 --- a/pyomo/contrib/latex_printer/latex_printer.py +++ b/pyomo/contrib/latex_printer/latex_printer.py @@ -47,7 +47,7 @@ resolve_template, templatize_rule, ) -from pyomo.core.base.var import ScalarVar, GeneralVarData, IndexedVar +from pyomo.core.base.var import ScalarVar, VarData, IndexedVar from pyomo.core.base.param import ParamData, ScalarParam, IndexedParam from pyomo.core.base.set import SetData, SetOperator from pyomo.core.base.constraint import ScalarConstraint, IndexedConstraint @@ -404,7 +404,7 @@ def __init__(self): kernel.expression.expression: handle_named_expression_node, kernel.expression.noclone: handle_named_expression_node, GeneralObjectiveData: handle_named_expression_node, - GeneralVarData: handle_var_node, + VarData: handle_var_node, ScalarObjective: handle_named_expression_node, kernel.objective.objective: handle_named_expression_node, ExternalFunctionExpression: handle_external_function_node, @@ -705,10 +705,8 @@ def latex_printer( if isSingle: temp_comp, temp_indexes = templatize_fcn(pyomo_component) variableList = [] - for v in identify_components( - temp_comp, [ScalarVar, GeneralVarData, IndexedVar] - ): - if isinstance(v, GeneralVarData): + for v in identify_components(temp_comp, [ScalarVar, VarData, IndexedVar]): + if isinstance(v, VarData): v_write = v.parent_component() if v_write not in ComponentSet(variableList): variableList.append(v_write) @@ -1273,7 +1271,7 @@ def get_index_names(st, lcm): rep_dict = {} for ky in reversed(list(latex_component_map)): - if isinstance(ky, (pyo.Var, GeneralVarData)): + if isinstance(ky, (pyo.Var, VarData)): overwrite_value = latex_component_map[ky] if ky not in existing_components: overwrite_value = overwrite_value.replace('_', '\\_') diff --git a/pyomo/contrib/parmest/utils/scenario_tree.py b/pyomo/contrib/parmest/utils/scenario_tree.py index 1062e4a2bf4..f245e053cad 100644 --- a/pyomo/contrib/parmest/utils/scenario_tree.py +++ b/pyomo/contrib/parmest/utils/scenario_tree.py @@ -25,7 +25,7 @@ def build_vardatalist(self, model, varlist=None): """ - Convert a list of pyomo variables to a list of ScalarVar and GeneralVarData. If varlist is none, builds a + Convert a list of pyomo variables to a list of ScalarVar and VarData. If varlist is none, builds a list of all variables in the model. The new list is stored in the vars_to_tighten attribute. By CD Laird Parameters diff --git a/pyomo/contrib/solver/base.py b/pyomo/contrib/solver/base.py index 1b22c17cf48..fdc7361e6b8 100644 --- a/pyomo/contrib/solver/base.py +++ b/pyomo/contrib/solver/base.py @@ -15,7 +15,7 @@ import os from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.param import ParamData from pyomo.core.base.block import BlockData from pyomo.core.base.objective import GeneralObjectiveData @@ -194,9 +194,7 @@ def is_persistent(self): """ return True - def _load_vars( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> NoReturn: + def _load_vars(self, vars_to_load: Optional[Sequence[VarData]] = None) -> NoReturn: """ Load the solution of the primal variables into the value attribute of the variables. @@ -212,19 +210,19 @@ def _load_vars( @abc.abstractmethod def _get_primals( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: """ Get mapping of variables to primals. Parameters ---------- - vars_to_load : Optional[Sequence[GeneralVarData]], optional + vars_to_load : Optional[Sequence[VarData]], optional Which vars to be populated into the map. The default is None. Returns ------- - Mapping[GeneralVarData, float] + Mapping[VarData, float] A map of variables to primals. """ raise NotImplementedError( @@ -251,8 +249,8 @@ def _get_duals( raise NotImplementedError(f'{type(self)} does not support the get_duals method') def _get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: """ Parameters ---------- @@ -282,7 +280,7 @@ def set_objective(self, obj: GeneralObjectiveData): """ @abc.abstractmethod - def add_variables(self, variables: List[GeneralVarData]): + def add_variables(self, variables: List[VarData]): """ Add variables to the model """ @@ -306,7 +304,7 @@ def add_block(self, block: BlockData): """ @abc.abstractmethod - def remove_variables(self, variables: List[GeneralVarData]): + def remove_variables(self, variables: List[VarData]): """ Remove variables from the model """ @@ -330,7 +328,7 @@ def remove_block(self, block: BlockData): """ @abc.abstractmethod - def update_variables(self, variables: List[GeneralVarData]): + def update_variables(self, variables: List[VarData]): """ Update variables on the model """ diff --git a/pyomo/contrib/solver/gurobi.py b/pyomo/contrib/solver/gurobi.py index c5a1c8c1cd8..ff4e93f7635 100644 --- a/pyomo/contrib/solver/gurobi.py +++ b/pyomo/contrib/solver/gurobi.py @@ -22,7 +22,7 @@ from pyomo.common.config import ConfigValue from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.param import ParamData @@ -438,7 +438,7 @@ def _process_domain_and_bounds( return lb, ub, vtype - def _add_variables(self, variables: List[GeneralVarData]): + def _add_variables(self, variables: List[VarData]): var_names = list() vtypes = list() lbs = list() @@ -735,7 +735,7 @@ def _remove_sos_constraints(self, cons: List[SOSConstraintData]): del self._pyomo_sos_to_solver_sos_map[con] self._needs_updated = True - def _remove_variables(self, variables: List[GeneralVarData]): + def _remove_variables(self, variables: List[VarData]): for var in variables: v_id = id(var) if var in self._vars_added_since_update: @@ -750,7 +750,7 @@ def _remove_variables(self, variables: List[GeneralVarData]): def _remove_parameters(self, params: List[ParamData]): pass - def _update_variables(self, variables: List[GeneralVarData]): + def _update_variables(self, variables: List[VarData]): for var in variables: var_id = id(var) if var_id not in self._pyomo_var_to_solver_var_map: @@ -1151,7 +1151,7 @@ def set_var_attr(self, var, attr, val): Parameters ---------- - var: pyomo.core.base.var.GeneralVarData + var: pyomo.core.base.var.VarData The pyomo var for which the corresponding gurobi var attribute should be modified. attr: str @@ -1186,7 +1186,7 @@ def get_var_attr(self, var, attr): Parameters ---------- - var: pyomo.core.base.var.GeneralVarData + var: pyomo.core.base.var.VarData The pyomo var for which the corresponding gurobi var attribute should be retrieved. attr: str diff --git a/pyomo/contrib/solver/ipopt.py b/pyomo/contrib/solver/ipopt.py index 7111ec6e972..e4d25e4fea0 100644 --- a/pyomo/contrib/solver/ipopt.py +++ b/pyomo/contrib/solver/ipopt.py @@ -25,7 +25,7 @@ ) from pyomo.common.tempfiles import TempfileManager from pyomo.common.timing import HierarchicalTimer -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.staleflag import StaleFlagManager from pyomo.repn.plugins.nl_writer import NLWriter, NLWriterInfo from pyomo.contrib.solver.base import SolverBase @@ -80,8 +80,8 @@ def __init__( class IpoptSolutionLoader(SolSolutionLoader): def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if self._nl_info is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' diff --git a/pyomo/contrib/solver/persistent.py b/pyomo/contrib/solver/persistent.py index e98d76b4841..103eb3c622f 100644 --- a/pyomo/contrib/solver/persistent.py +++ b/pyomo/contrib/solver/persistent.py @@ -14,7 +14,7 @@ from pyomo.core.base.constraint import GeneralConstraintData, Constraint from pyomo.core.base.sos import SOSConstraintData, SOSConstraint -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.param import ParamData, Param from pyomo.core.base.objective import GeneralObjectiveData from pyomo.common.collections import ComponentMap @@ -54,10 +54,10 @@ def set_instance(self, model): self.set_objective(None) @abc.abstractmethod - def _add_variables(self, variables: List[GeneralVarData]): + def _add_variables(self, variables: List[VarData]): pass - def add_variables(self, variables: List[GeneralVarData]): + def add_variables(self, variables: List[VarData]): for v in variables: if id(v) in self._referenced_variables: raise ValueError( @@ -87,7 +87,7 @@ def add_parameters(self, params: List[ParamData]): def _add_constraints(self, cons: List[GeneralConstraintData]): pass - def _check_for_new_vars(self, variables: List[GeneralVarData]): + def _check_for_new_vars(self, variables: List[VarData]): new_vars = {} for v in variables: v_id = id(v) @@ -95,7 +95,7 @@ def _check_for_new_vars(self, variables: List[GeneralVarData]): new_vars[v_id] = v self.add_variables(list(new_vars.values())) - def _check_to_remove_vars(self, variables: List[GeneralVarData]): + def _check_to_remove_vars(self, variables: List[VarData]): vars_to_remove = {} for v in variables: v_id = id(v) @@ -250,10 +250,10 @@ def remove_sos_constraints(self, cons: List[SOSConstraintData]): del self._vars_referenced_by_con[con] @abc.abstractmethod - def _remove_variables(self, variables: List[GeneralVarData]): + def _remove_variables(self, variables: List[VarData]): pass - def remove_variables(self, variables: List[GeneralVarData]): + def remove_variables(self, variables: List[VarData]): self._remove_variables(variables) for v in variables: v_id = id(v) @@ -309,10 +309,10 @@ def remove_block(self, block): ) @abc.abstractmethod - def _update_variables(self, variables: List[GeneralVarData]): + def _update_variables(self, variables: List[VarData]): pass - def update_variables(self, variables: List[GeneralVarData]): + def update_variables(self, variables: List[VarData]): for v in variables: self._vars[id(v)] = ( v, diff --git a/pyomo/contrib/solver/solution.py b/pyomo/contrib/solver/solution.py index 3f327c1f280..e089e621f1f 100644 --- a/pyomo/contrib/solver/solution.py +++ b/pyomo/contrib/solver/solution.py @@ -13,7 +13,7 @@ from typing import Sequence, Dict, Optional, Mapping, NoReturn from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.expr import value from pyomo.common.collections import ComponentMap from pyomo.common.errors import DeveloperError @@ -30,9 +30,7 @@ class SolutionLoaderBase(abc.ABC): Intent of this class and its children is to load the solution back into the model. """ - def load_vars( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> NoReturn: + def load_vars(self, vars_to_load: Optional[Sequence[VarData]] = None) -> NoReturn: """ Load the solution of the primal variables into the value attribute of the variables. @@ -49,8 +47,8 @@ def load_vars( @abc.abstractmethod def get_primals( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: """ Returns a ComponentMap mapping variable to var value. @@ -86,8 +84,8 @@ def get_duals( raise NotImplementedError(f'{type(self)} does not support the get_duals method') def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: """ Returns a ComponentMap mapping variable to reduced cost. @@ -127,8 +125,8 @@ def get_duals( return self._solver._get_duals(cons_to_load=cons_to_load) def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: self._assert_solution_still_valid() return self._solver._get_reduced_costs(vars_to_load=vars_to_load) @@ -141,9 +139,7 @@ def __init__(self, sol_data: SolFileData, nl_info: NLWriterInfo) -> None: self._sol_data = sol_data self._nl_info = nl_info - def load_vars( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> NoReturn: + def load_vars(self, vars_to_load: Optional[Sequence[VarData]] = None) -> NoReturn: if self._nl_info is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' @@ -169,8 +165,8 @@ def load_vars( StaleFlagManager.mark_all_as_stale(delayed=True) def get_primals( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if self._nl_info is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' diff --git a/pyomo/contrib/solver/tests/unit/test_results.py b/pyomo/contrib/solver/tests/unit/test_results.py index 608af04a0ed..6c178d80298 100644 --- a/pyomo/contrib/solver/tests/unit/test_results.py +++ b/pyomo/contrib/solver/tests/unit/test_results.py @@ -16,7 +16,7 @@ from pyomo.common import unittest from pyomo.common.config import ConfigDict from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.common.collections import ComponentMap from pyomo.contrib.solver import results from pyomo.contrib.solver import solution @@ -51,8 +51,8 @@ def __init__( self._reduced_costs = reduced_costs def get_primals( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if self._primals is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' @@ -84,8 +84,8 @@ def get_duals( return duals def get_reduced_costs( - self, vars_to_load: Optional[Sequence[GeneralVarData]] = None - ) -> Mapping[GeneralVarData, float]: + self, vars_to_load: Optional[Sequence[VarData]] = None + ) -> Mapping[VarData, float]: if self._reduced_costs is None: raise RuntimeError( 'Solution loader does not currently have valid reduced costs. Please ' diff --git a/pyomo/contrib/trustregion/tests/test_interface.py b/pyomo/contrib/trustregion/tests/test_interface.py index 64f76eb887d..0922ccf950b 100644 --- a/pyomo/contrib/trustregion/tests/test_interface.py +++ b/pyomo/contrib/trustregion/tests/test_interface.py @@ -33,7 +33,7 @@ cos, SolverFactory, ) -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.expr.numeric_expr import ExternalFunctionExpression from pyomo.core.expr.visitor import identify_variables from pyomo.contrib.trustregion.interface import TRFInterface @@ -158,7 +158,7 @@ def test_replaceExternalFunctionsWithVariables(self): self.assertIsInstance(k, ExternalFunctionExpression) self.assertIn(str(self.interface.model.x[0]), str(k)) self.assertIn(str(self.interface.model.x[1]), str(k)) - self.assertIsInstance(i, GeneralVarData) + self.assertIsInstance(i, VarData) self.assertEqual(i, self.interface.data.ef_outputs[1]) for i, k in self.interface.data.basis_expressions.items(): self.assertEqual(k, 0) diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 9a06a3e02bb..6851fe4cda0 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -40,7 +40,6 @@ from pyomo.core.base.componentuid import ComponentUID from pyomo.core.base.config import PyomoOptions from pyomo.core.base.enums import SortComponents, TraversalStrategy -from pyomo.core.base.instance2dat import instance2dat from pyomo.core.base.label import ( CuidLabeler, CounterLabeler, @@ -146,7 +145,9 @@ active_import_suffix_generator, Suffix, ) -from pyomo.core.base.var import Var, VarData, GeneralVarData, ScalarVar, VarList +from pyomo.core.base.var import Var, VarData, VarData, ScalarVar, VarList + +from pyomo.core.base.instance2dat import instance2dat # # These APIs are deprecated and should be removed in the near future @@ -163,12 +164,14 @@ 'SimpleBooleanVar', 'pyomo.core.base.boolean_var.SimpleBooleanVar', version='6.0' ) # Historically, only a subset of "private" component data classes were imported here +relocated_module_attribute( + f'_GeneralVarData', f'pyomo.core.base.VarData', version='6.7.2.dev0' +) for _cdata in ( 'ConstraintData', 'LogicalConstraintData', 'ExpressionData', 'VarData', - 'GeneralVarData', 'GeneralBooleanVarData', 'BooleanVarData', 'ObjectiveData', diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 7a4b7e40aab..65844379eca 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -805,7 +805,7 @@ class ComponentData(_ComponentBase): # classes: BooleanVarData, ConnectorData, ConstraintData, # GeneralExpressionData, LogicalConstraintData, # GeneralLogicalConstraintData, GeneralObjectiveData, - # ParamData,GeneralVarData, GeneralBooleanVarData, DisjunctionData, + # ParamData,VarData, GeneralBooleanVarData, DisjunctionData, # ArcData, PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those # constructors as well! diff --git a/pyomo/core/expr/calculus/derivatives.py b/pyomo/core/expr/calculus/derivatives.py index 5df1fd3c65e..69fe4969938 100644 --- a/pyomo/core/expr/calculus/derivatives.py +++ b/pyomo/core/expr/calculus/derivatives.py @@ -39,11 +39,11 @@ def differentiate(expr, wrt=None, wrt_list=None, mode=Modes.reverse_numeric): ---------- expr: pyomo.core.expr.numeric_expr.NumericExpression The expression to differentiate - wrt: pyomo.core.base.var.GeneralVarData + wrt: pyomo.core.base.var.VarData If specified, this function will return the derivative with - respect to wrt. wrt is normally a GeneralVarData, but could + respect to wrt. wrt is normally a VarData, but could also be a ParamData. wrt and wrt_list cannot both be specified. - wrt_list: list of pyomo.core.base.var.GeneralVarData + wrt_list: list of pyomo.core.base.var.VarData If specified, this function will return the derivative with respect to each element in wrt_list. A list will be returned where the values are the derivatives with respect to the diff --git a/pyomo/core/tests/transform/test_add_slacks.py b/pyomo/core/tests/transform/test_add_slacks.py index d66d6fba79e..b395237b8e4 100644 --- a/pyomo/core/tests/transform/test_add_slacks.py +++ b/pyomo/core/tests/transform/test_add_slacks.py @@ -330,7 +330,7 @@ def test_error_for_non_constraint_noniterable_target(self): self.assertRaisesRegex( ValueError, "Expected Constraint or list of Constraints.\n\tReceived " - "", + "", TransformationFactory('core.add_slack_variables').apply_to, m, targets=m.indexedVar[1], diff --git a/pyomo/core/tests/unit/test_dict_objects.py b/pyomo/core/tests/unit/test_dict_objects.py index f2c3cad8cc3..0dc5cacd216 100644 --- a/pyomo/core/tests/unit/test_dict_objects.py +++ b/pyomo/core/tests/unit/test_dict_objects.py @@ -17,7 +17,7 @@ ObjectiveDict, ExpressionDict, ) -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.expression import GeneralExpressionData @@ -348,10 +348,10 @@ def test_active(self): class TestVarDict(_TestComponentDictBase, unittest.TestCase): - # Note: the updated GeneralVarData class only takes an optional + # Note: the updated VarData class only takes an optional # parent argument (you no longer pass the domain in) _ctype = VarDict - _cdatatype = lambda self, arg: GeneralVarData() + _cdatatype = lambda self, arg: VarData() def setUp(self): _TestComponentDictBase.setUp(self) diff --git a/pyomo/core/tests/unit/test_list_objects.py b/pyomo/core/tests/unit/test_list_objects.py index fcc83a95a06..f98b5279fc5 100644 --- a/pyomo/core/tests/unit/test_list_objects.py +++ b/pyomo/core/tests/unit/test_list_objects.py @@ -17,7 +17,7 @@ XObjectiveList, XExpressionList, ) -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import GeneralObjectiveData from pyomo.core.base.expression import GeneralExpressionData @@ -365,10 +365,10 @@ def test_active(self): class TestVarList(_TestComponentListBase, unittest.TestCase): - # Note: the updated GeneralVarData class only takes an optional + # Note: the updated VarData class only takes an optional # parent argument (you no longer pass the domain in) _ctype = XVarList - _cdatatype = lambda self, arg: GeneralVarData() + _cdatatype = lambda self, arg: VarData() def setUp(self): _TestComponentListBase.setUp(self) diff --git a/pyomo/core/tests/unit/test_numeric_expr.py b/pyomo/core/tests/unit/test_numeric_expr.py index 8e5e43eac9c..efb01e6d6ce 100644 --- a/pyomo/core/tests/unit/test_numeric_expr.py +++ b/pyomo/core/tests/unit/test_numeric_expr.py @@ -112,7 +112,7 @@ from pyomo.core.base.label import NumericLabeler from pyomo.core.expr.template_expr import IndexTemplate from pyomo.core.expr import expr_common -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.repn import generate_standard_repn from pyomo.core.expr.numvalue import NumericValue @@ -294,7 +294,7 @@ def value_check(self, exp, val): class TestExpression_EvaluateVarData(TestExpression_EvaluateNumericValue): def create(self, val, domain): - tmp = GeneralVarData() + tmp = VarData() tmp.domain = domain tmp.value = val return tmp diff --git a/pyomo/core/tests/unit/test_reference.py b/pyomo/core/tests/unit/test_reference.py index 4fa2f4944e9..7370881612f 100644 --- a/pyomo/core/tests/unit/test_reference.py +++ b/pyomo/core/tests/unit/test_reference.py @@ -800,8 +800,8 @@ def test_reference_indexedcomponent_pprint(self): buf.getvalue(), """r : Size=2, Index={1, 2}, ReferenceTo=x Key : Object - 1 : - 2 : + 1 : + 2 : """, ) m.s = Reference(m.x[:, ...], ctype=IndexedComponent) @@ -811,8 +811,8 @@ def test_reference_indexedcomponent_pprint(self): buf.getvalue(), """s : Size=2, Index={1, 2}, ReferenceTo=x[:, ...] Key : Object - 1 : - 2 : + 1 : + 2 : """, ) @@ -1357,8 +1357,8 @@ def test_pprint_nonfinite_sets_ctypeNone(self): 1 IndexedComponent Declarations ref : Size=2, Index=NonNegativeIntegers, ReferenceTo=v Key : Object - 3 : - 5 : + 3 : + 5 : 2 Declarations: v ref """.strip(), diff --git a/pyomo/repn/standard_repn.py b/pyomo/repn/standard_repn.py index 5786d078385..2f5a413e963 100644 --- a/pyomo/repn/standard_repn.py +++ b/pyomo/repn/standard_repn.py @@ -22,7 +22,7 @@ from pyomo.core.base.objective import GeneralObjectiveData, ScalarObjective from pyomo.core.base import ExpressionData, Expression from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData -from pyomo.core.base.var import ScalarVar, Var, GeneralVarData, value +from pyomo.core.base.var import ScalarVar, Var, VarData, value from pyomo.core.base.param import ScalarParam, ParamData from pyomo.core.kernel.expression import expression, noclone from pyomo.core.kernel.variable import IVariable, variable @@ -1143,7 +1143,7 @@ def _collect_external_fn(exp, multiplier, idMap, compute_values, verbose, quadra # param.Param : _collect_linear_const, # parameter : _collect_linear_const, NumericConstant: _collect_const, - GeneralVarData: _collect_var, + VarData: _collect_var, ScalarVar: _collect_var, Var: _collect_var, variable: _collect_var, @@ -1542,7 +1542,7 @@ def _linear_collect_pow(exp, multiplier, idMap, compute_values, verbose, coef): ##param.ScalarParam : _collect_linear_const, ##param.Param : _collect_linear_const, ##parameter : _collect_linear_const, - GeneralVarData : _linear_collect_var, + VarData : _linear_collect_var, ScalarVar : _linear_collect_var, Var : _linear_collect_var, variable : _linear_collect_var, diff --git a/pyomo/solvers/plugins/solvers/gurobi_persistent.py b/pyomo/solvers/plugins/solvers/gurobi_persistent.py index 97a3533c3f9..17ce33fd95f 100644 --- a/pyomo/solvers/plugins/solvers/gurobi_persistent.py +++ b/pyomo/solvers/plugins/solvers/gurobi_persistent.py @@ -192,7 +192,7 @@ def set_var_attr(self, var, attr, val): Parameters ---------- - con: pyomo.core.base.var.GeneralVarData + con: pyomo.core.base.var.VarData The pyomo var for which the corresponding gurobi var attribute should be modified. attr: str @@ -342,7 +342,7 @@ def get_var_attr(self, var, attr): Parameters ---------- - var: pyomo.core.base.var.GeneralVarData + var: pyomo.core.base.var.VarData The pyomo var for which the corresponding gurobi var attribute should be retrieved. attr: str diff --git a/pyomo/util/report_scaling.py b/pyomo/util/report_scaling.py index 265564bf12d..7619662c482 100644 --- a/pyomo/util/report_scaling.py +++ b/pyomo/util/report_scaling.py @@ -13,7 +13,7 @@ import math from pyomo.core.base.block import BlockData from pyomo.common.collections import ComponentSet -from pyomo.core.base.var import GeneralVarData +from pyomo.core.base.var import VarData from pyomo.contrib.fbbt.fbbt import compute_bounds_on_expr from pyomo.core.expr.calculus.diff_with_pyomo import reverse_sd import logging @@ -73,7 +73,7 @@ def _check_coefficients( ): ders = reverse_sd(expr) for _v, _der in ders.items(): - if isinstance(_v, GeneralVarData): + if isinstance(_v, VarData): if _v.is_fixed(): continue der_lb, der_ub = compute_bounds_on_expr(_der) From 458c84e5acabcb95186c780238ec7f951b4e54b4 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 20:29:24 -0600 Subject: [PATCH 35/83] Merge GeneralBooleanVarData into BooelanVarData class --- pyomo/core/base/boolean_var.py | 205 +++++++++++++-------------------- 1 file changed, 78 insertions(+), 127 deletions(-) diff --git a/pyomo/core/base/boolean_var.py b/pyomo/core/base/boolean_var.py index 925dca530a7..b6a25cd8f27 100644 --- a/pyomo/core/base/boolean_var.py +++ b/pyomo/core/base/boolean_var.py @@ -68,27 +68,61 @@ def __setstate__(self, state): self._boolvar = weakref_ref(state) +def _associated_binary_mapper(encode, val): + if val is None: + return None + if encode: + if val.__class__ is not _DeprecatedImplicitAssociatedBinaryVariable: + return val() + else: + if val.__class__ is not _DeprecatedImplicitAssociatedBinaryVariable: + return weakref_ref(val) + return val + + class BooleanVarData(ComponentData, BooleanValue): """ - This class defines the data for a single variable. + This class defines the data for a single Boolean variable. Constructor Arguments: component The BooleanVar object that owns this data. + Public Class Attributes: + domain The domain of this variable. fixed If True, then this variable is treated as a fixed constant in the model. stale A Boolean indicating whether the value of this variable is - legitimate. This value is true if the value should + legitimiate. This value is true if the value should be considered legitimate for purposes of reporting or other interrogation. value The numeric value of this variable. + + The domain attribute is a property because it is + too widely accessed directly to enforce explicit getter/setter + methods and we need to deter directly modifying or accessing + these attributes in certain cases. """ - __slots__ = () + __slots__ = ('_value', 'fixed', '_stale', '_associated_binary') + __autoslot_mappers__ = { + '_associated_binary': _associated_binary_mapper, + '_stale': StaleFlagManager.stale_mapper, + } def __init__(self, component=None): + # + # These lines represent in-lining of the + # following constructors: + # - BooleanVarData + # - ComponentData + # - BooleanValue self._component = weakref_ref(component) if (component is not None) else None self._index = NOTSET + self._value = None + self.fixed = False + self._stale = 0 # True + + self._associated_binary = None def is_fixed(self): """Returns True if this variable is fixed, otherwise returns False.""" @@ -132,118 +166,6 @@ def __call__(self, exception=True): """Compute the value of this variable.""" return self.value - @property - def value(self): - """Return the value for this variable.""" - raise NotImplementedError - - @property - def domain(self): - """Return the domain for this variable.""" - raise NotImplementedError - - @property - def fixed(self): - """Return the fixed indicator for this variable.""" - raise NotImplementedError - - @property - def stale(self): - """Return the stale indicator for this variable.""" - raise NotImplementedError - - def fix(self, value=NOTSET, skip_validation=False): - """Fix the value of this variable (treat as nonvariable) - - This sets the `fixed` indicator to True. If ``value`` is - provided, the value (and the ``skip_validation`` flag) are first - passed to :py:meth:`set_value()`. - - """ - self.fixed = True - if value is not NOTSET: - self.set_value(value, skip_validation) - - def unfix(self): - """Unfix this variable (treat as variable) - - This sets the `fixed` indicator to False. - - """ - self.fixed = False - - def free(self): - """Alias for :py:meth:`unfix`""" - return self.unfix() - - -class _BooleanVarData(metaclass=RenamedClass): - __renamed__new_class__ = BooleanVarData - __renamed__version__ = '6.7.2.dev0' - - -def _associated_binary_mapper(encode, val): - if val is None: - return None - if encode: - if val.__class__ is not _DeprecatedImplicitAssociatedBinaryVariable: - return val() - else: - if val.__class__ is not _DeprecatedImplicitAssociatedBinaryVariable: - return weakref_ref(val) - return val - - -class GeneralBooleanVarData(BooleanVarData): - """ - This class defines the data for a single Boolean variable. - - Constructor Arguments: - component The BooleanVar object that owns this data. - - Public Class Attributes: - domain The domain of this variable. - fixed If True, then this variable is treated as a - fixed constant in the model. - stale A Boolean indicating whether the value of this variable is - legitimiate. This value is true if the value should - be considered legitimate for purposes of reporting or - other interrogation. - value The numeric value of this variable. - - The domain attribute is a property because it is - too widely accessed directly to enforce explicit getter/setter - methods and we need to deter directly modifying or accessing - these attributes in certain cases. - """ - - __slots__ = ('_value', 'fixed', '_stale', '_associated_binary') - __autoslot_mappers__ = { - '_associated_binary': _associated_binary_mapper, - '_stale': StaleFlagManager.stale_mapper, - } - - def __init__(self, component=None): - # - # These lines represent in-lining of the - # following constructors: - # - BooleanVarData - # - ComponentData - # - BooleanValue - self._component = weakref_ref(component) if (component is not None) else None - self._index = NOTSET - self._value = None - self.fixed = False - self._stale = 0 # True - - self._associated_binary = None - - # - # Abstract Interface - # - - # value is an attribute - @property def value(self): """Return (or set) the value for this variable.""" @@ -271,13 +193,13 @@ def stale(self, val): def get_associated_binary(self): """Get the binary VarData associated with this - GeneralBooleanVarData""" + BooleanVarData""" return ( self._associated_binary() if self._associated_binary is not None else None ) def associate_binary_var(self, binary_var): - """Associate a binary VarData to this GeneralBooleanVarData""" + """Associate a binary VarData to this BooleanVarData""" if ( self._associated_binary is not None and type(self._associated_binary) @@ -299,9 +221,38 @@ def associate_binary_var(self, binary_var): if binary_var is not None: self._associated_binary = weakref_ref(binary_var) + def fix(self, value=NOTSET, skip_validation=False): + """Fix the value of this variable (treat as nonvariable) + + This sets the `fixed` indicator to True. If ``value`` is + provided, the value (and the ``skip_validation`` flag) are first + passed to :py:meth:`set_value()`. + + """ + self.fixed = True + if value is not NOTSET: + self.set_value(value, skip_validation) + + def unfix(self): + """Unfix this variable (treat as variable) + + This sets the `fixed` indicator to False. -class _GeneralBooleanVarData(metaclass=RenamedClass): - __renamed__new_class__ = GeneralBooleanVarData + """ + self.fixed = False + + def free(self): + """Alias for :py:meth:`unfix`""" + return self.unfix() + + +class _BooleanVarData(metaclass=RenamedClass): + __renamed__new_class__ = BooleanVarData + __renamed__version__ = '6.7.2.dev0' + + +class _BooleanVarData(metaclass=RenamedClass): + __renamed__new_class__ = BooleanVarData __renamed__version__ = '6.7.2.dev0' @@ -319,7 +270,7 @@ class BooleanVar(IndexedComponent): to True. """ - _ComponentDataClass = GeneralBooleanVarData + _ComponentDataClass = BooleanVarData def __new__(cls, *args, **kwds): if cls != BooleanVar: @@ -511,11 +462,11 @@ def _pprint(self): ) -class ScalarBooleanVar(GeneralBooleanVarData, BooleanVar): +class ScalarBooleanVar(BooleanVarData, BooleanVar): """A single variable.""" def __init__(self, *args, **kwd): - GeneralBooleanVarData.__init__(self, component=self) + BooleanVarData.__init__(self, component=self) BooleanVar.__init__(self, *args, **kwd) self._index = UnindexedComponent_index @@ -531,7 +482,7 @@ def __init__(self, *args, **kwd): def value(self): """Return the value for this variable.""" if self._constructed: - return GeneralBooleanVarData.value.fget(self) + return BooleanVarData.value.fget(self) raise ValueError( "Accessing the value of variable '%s' " "before the Var has been constructed (there " @@ -542,7 +493,7 @@ def value(self): def value(self, val): """Set the value for this variable.""" if self._constructed: - return GeneralBooleanVarData.value.fset(self, val) + return BooleanVarData.value.fset(self, val) raise ValueError( "Setting the value of variable '%s' " "before the Var has been constructed (there " @@ -551,7 +502,7 @@ def value(self, val): @property def domain(self): - return GeneralBooleanVarData.domain.fget(self) + return BooleanVarData.domain.fget(self) def fix(self, value=NOTSET, skip_validation=False): """ @@ -559,7 +510,7 @@ def fix(self, value=NOTSET, skip_validation=False): indicating the variable should be fixed at its current value. """ if self._constructed: - return GeneralBooleanVarData.fix(self, value, skip_validation) + return BooleanVarData.fix(self, value, skip_validation) raise ValueError( "Fixing variable '%s' " "before the Var has been constructed (there " @@ -569,7 +520,7 @@ def fix(self, value=NOTSET, skip_validation=False): def unfix(self): """Sets the fixed indicator to False.""" if self._constructed: - return GeneralBooleanVarData.unfix(self) + return BooleanVarData.unfix(self) raise ValueError( "Freeing variable '%s' " "before the Var has been constructed (there " From 015a4f859d63d9cdf615a488490301f88a2c96cc Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 20:30:30 -0600 Subject: [PATCH 36/83] Update references from GeneralBooleanVarData to BooelanVarData --- pyomo/contrib/cp/repn/docplex_writer.py | 4 ++-- pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py | 2 +- pyomo/core/base/__init__.py | 6 ++++-- pyomo/core/base/boolean_var.py | 2 +- pyomo/core/base/component.py | 2 +- 5 files changed, 9 insertions(+), 7 deletions(-) diff --git a/pyomo/contrib/cp/repn/docplex_writer.py b/pyomo/contrib/cp/repn/docplex_writer.py index 221fd61af5b..1af153910c0 100644 --- a/pyomo/contrib/cp/repn/docplex_writer.py +++ b/pyomo/contrib/cp/repn/docplex_writer.py @@ -60,7 +60,7 @@ ) from pyomo.core.base.boolean_var import ( ScalarBooleanVar, - GeneralBooleanVarData, + BooleanVarData, IndexedBooleanVar, ) from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData @@ -964,7 +964,7 @@ class LogicalToDoCplex(StreamBasedExpressionVisitor): VarData: _before_var, IndexedVar: _before_indexed_var, ScalarBooleanVar: _before_boolean_var, - GeneralBooleanVarData: _before_boolean_var, + BooleanVarData: _before_boolean_var, IndexedBooleanVar: _before_indexed_boolean_var, GeneralExpressionData: _before_named_expression, ScalarExpression: _before_named_expression, diff --git a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py index d9483c0ed14..0c493b89321 100644 --- a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py +++ b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py @@ -209,7 +209,7 @@ def _dispatch_atmost(visitor, node, *args): _before_child_dispatcher = {} _before_child_dispatcher[BV.ScalarBooleanVar] = _dispatch_boolean_var -_before_child_dispatcher[BV.GeneralBooleanVarData] = _dispatch_boolean_var +_before_child_dispatcher[BV.BooleanVarData] = _dispatch_boolean_var _before_child_dispatcher[AutoLinkedBooleanVar] = _dispatch_boolean_var _before_child_dispatcher[ParamData] = _dispatch_param _before_child_dispatcher[ScalarParam] = _dispatch_param diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 6851fe4cda0..bcc2a0e0e02 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -84,7 +84,7 @@ from pyomo.core.base.boolean_var import ( BooleanVar, BooleanVarData, - GeneralBooleanVarData, + BooleanVarData, BooleanVarList, ScalarBooleanVar, ) @@ -167,12 +167,14 @@ relocated_module_attribute( f'_GeneralVarData', f'pyomo.core.base.VarData', version='6.7.2.dev0' ) +relocated_module_attribute( + f'_GeneralBooleanVarData', f'pyomo.core.base.BooleanVarData', version='6.7.2.dev0' +) for _cdata in ( 'ConstraintData', 'LogicalConstraintData', 'ExpressionData', 'VarData', - 'GeneralBooleanVarData', 'BooleanVarData', 'ObjectiveData', ): diff --git a/pyomo/core/base/boolean_var.py b/pyomo/core/base/boolean_var.py index b6a25cd8f27..98761dee536 100644 --- a/pyomo/core/base/boolean_var.py +++ b/pyomo/core/base/boolean_var.py @@ -251,7 +251,7 @@ class _BooleanVarData(metaclass=RenamedClass): __renamed__version__ = '6.7.2.dev0' -class _BooleanVarData(metaclass=RenamedClass): +class _GeneralBooleanVarData(metaclass=RenamedClass): __renamed__new_class__ = BooleanVarData __renamed__version__ = '6.7.2.dev0' diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 65844379eca..1c73809a25a 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -805,7 +805,7 @@ class ComponentData(_ComponentBase): # classes: BooleanVarData, ConnectorData, ConstraintData, # GeneralExpressionData, LogicalConstraintData, # GeneralLogicalConstraintData, GeneralObjectiveData, - # ParamData,VarData, GeneralBooleanVarData, DisjunctionData, + # ParamData,VarData, BooleanVarData, DisjunctionData, # ArcData, PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those # constructors as well! From 0cbfcb7418310b2dbb97aa6e915d4570e02c1d37 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 20:38:00 -0600 Subject: [PATCH 37/83] Restore deprecation path for GeneralVarData --- pyomo/core/base/var.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyomo/core/base/var.py b/pyomo/core/base/var.py index b1634b61c44..8870fc5b09c 100644 --- a/pyomo/core/base/var.py +++ b/pyomo/core/base/var.py @@ -575,7 +575,7 @@ class _VarData(metaclass=RenamedClass): __renamed__version__ = '6.7.2.dev0' -class _VarData(metaclass=RenamedClass): +class _GeneralVarData(metaclass=RenamedClass): __renamed__new_class__ = VarData __renamed__version__ = '6.7.2.dev0' From adfe72b6ff4a6900f98d77dad7cac83da7e41250 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 20:38:35 -0600 Subject: [PATCH 38/83] Merge GeneralLogicalConstraintData into LogicalConstratintData --- pyomo/core/base/component.py | 2 +- pyomo/core/base/logical_constraint.py | 77 ++++----------------------- 2 files changed, 11 insertions(+), 68 deletions(-) diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 1c73809a25a..3dd4d47046d 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -804,7 +804,7 @@ class ComponentData(_ComponentBase): # NOTE: This constructor is in-lined in the constructors for the following # classes: BooleanVarData, ConnectorData, ConstraintData, # GeneralExpressionData, LogicalConstraintData, - # GeneralLogicalConstraintData, GeneralObjectiveData, + # LogicalConstraintData, GeneralObjectiveData, # ParamData,VarData, BooleanVarData, DisjunctionData, # ArcData, PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those diff --git a/pyomo/core/base/logical_constraint.py b/pyomo/core/base/logical_constraint.py index 23a422705df..1daa5f83e90 100644 --- a/pyomo/core/base/logical_constraint.py +++ b/pyomo/core/base/logical_constraint.py @@ -43,68 +43,6 @@ class LogicalConstraintData(ActiveComponentData): - """ - This class defines the data for a single logical constraint. - - It functions as a pure interface. - - Constructor arguments: - component The LogicalConstraint object that owns this data. - - Public class attributes: - active A boolean that is true if this statement is - active in the model. - body The Pyomo logical expression for this statement - - Private class attributes: - _component The statement component. - _active A boolean that indicates whether this data is active - """ - - __slots__ = () - - def __init__(self, component=None): - # - # These lines represent in-lining of the - # following constructors: - # - ActiveComponentData - # - ComponentData - self._component = weakref_ref(component) if (component is not None) else None - self._index = NOTSET - self._active = True - - # - # Interface - # - def __call__(self, exception=True): - """Compute the value of the body of this logical constraint.""" - if self.body is None: - return None - return self.body(exception=exception) - - # - # Abstract Interface - # - @property - def expr(self): - """Get the expression on this logical constraint.""" - raise NotImplementedError - - def set_value(self, expr): - """Set the expression on this logical constraint.""" - raise NotImplementedError - - def get_value(self): - """Get the expression on this logical constraint.""" - raise NotImplementedError - - -class _LogicalConstraintData(metaclass=RenamedClass): - __renamed__new_class__ = LogicalConstraintData - __renamed__version__ = '6.7.2.dev0' - - -class GeneralLogicalConstraintData(LogicalConstraintData): """ This class defines the data for a single general logical constraint. @@ -178,8 +116,13 @@ def get_value(self): return self._expr +class _LogicalConstraintData(metaclass=RenamedClass): + __renamed__new_class__ = LogicalConstraintData + __renamed__version__ = '6.7.2.dev0' + + class _GeneralLogicalConstraintData(metaclass=RenamedClass): - __renamed__new_class__ = GeneralLogicalConstraintData + __renamed__new_class__ = LogicalConstraintData __renamed__version__ = '6.7.2.dev0' @@ -225,7 +168,7 @@ class LogicalConstraint(ActiveIndexedComponent): The class type for the derived subclass """ - _ComponentDataClass = GeneralLogicalConstraintData + _ComponentDataClass = LogicalConstraintData class Infeasible(object): pass @@ -419,14 +362,14 @@ def _check_skip_add(self, index, expr): return expr -class ScalarLogicalConstraint(GeneralLogicalConstraintData, LogicalConstraint): +class ScalarLogicalConstraint(LogicalConstraintData, LogicalConstraint): """ ScalarLogicalConstraint is the implementation representing a single, non-indexed logical constraint. """ def __init__(self, *args, **kwds): - GeneralLogicalConstraintData.__init__(self, component=self, expr=None) + LogicalConstraintData.__init__(self, component=self, expr=None) LogicalConstraint.__init__(self, *args, **kwds) self._index = UnindexedComponent_index @@ -446,7 +389,7 @@ def body(self): "an expression. There is currently " "nothing to access." % self.name ) - return GeneralLogicalConstraintData.body.fget(self) + return LogicalConstraintData.body.fget(self) raise ValueError( "Accessing the body of logical constraint '%s' " "before the LogicalConstraint has been constructed (there " From a27b8791f864546444824e4d803c86e48b6de606 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 21:33:32 -0600 Subject: [PATCH 39/83] Merge GeneralObjectiveData into ObjectiveData --- pyomo/core/base/objective.py | 58 ++++++++---------------------------- 1 file changed, 12 insertions(+), 46 deletions(-) diff --git a/pyomo/core/base/objective.py b/pyomo/core/base/objective.py index 58cb198e1ae..e4956748b6c 100644 --- a/pyomo/core/base/objective.py +++ b/pyomo/core/base/objective.py @@ -81,51 +81,8 @@ def O_rule(model, i, j): return rule_wrapper(rule, {None: ObjectiveList.End}) -# -# This class is a pure interface -# - - -class ObjectiveData(ExpressionData): - """ - This class defines the data for a single objective. - - Public class attributes: - expr The Pyomo expression for this objective - sense The direction for this objective. - """ - - __slots__ = () - - # - # Interface - # - - def is_minimizing(self): - """Return True if this is a minimization objective.""" - return self.sense == minimize - - # - # Abstract Interface - # - - @property - def sense(self): - """Access sense (direction) of this objective.""" - raise NotImplementedError - - def set_sense(self, sense): - """Set the sense (direction) of this objective.""" - raise NotImplementedError - - -class _ObjectiveData(metaclass=RenamedClass): - __renamed__new_class__ = ObjectiveData - __renamed__version__ = '6.7.2.dev0' - - -class GeneralObjectiveData( - GeneralExpressionDataImpl, ObjectiveData, ActiveComponentData +class ObjectiveData( + GeneralExpressionDataImpl, ActiveComponentData ): """ This class defines the data for a single objective. @@ -166,6 +123,10 @@ def __init__(self, expr=None, sense=minimize, component=None): "value: %s'" % (minimize, maximize, sense) ) + def is_minimizing(self): + """Return True if this is a minimization objective.""" + return self.sense == minimize + def set_value(self, expr): if expr is None: raise ValueError(_rule_returned_none_error % (self.name,)) @@ -197,8 +158,13 @@ def set_sense(self, sense): ) +class _ObjectiveData(metaclass=RenamedClass): + __renamed__new_class__ = ObjectiveData + __renamed__version__ = '6.7.2.dev0' + + class _GeneralObjectiveData(metaclass=RenamedClass): - __renamed__new_class__ = GeneralObjectiveData + __renamed__new_class__ = ObjectiveData __renamed__version__ = '6.7.2.dev0' From 13c11e58a8b49de727e3a9d0eeb630b55a19f1be Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 21:38:00 -0600 Subject: [PATCH 40/83] Update references from GeneralObjectiveData to ObjectiveData --- pyomo/contrib/appsi/base.py | 8 ++++---- pyomo/contrib/appsi/fbbt.py | 6 +++--- pyomo/contrib/appsi/solvers/cbc.py | 4 ++-- pyomo/contrib/appsi/solvers/cplex.py | 4 ++-- pyomo/contrib/appsi/solvers/ipopt.py | 4 ++-- pyomo/contrib/appsi/writers/lp_writer.py | 4 ++-- pyomo/contrib/appsi/writers/nl_writer.py | 4 ++-- pyomo/contrib/community_detection/detection.py | 4 ++-- pyomo/contrib/latex_printer/latex_printer.py | 4 ++-- pyomo/contrib/solver/base.py | 4 ++-- pyomo/contrib/solver/persistent.py | 6 +++--- pyomo/core/base/component.py | 2 +- pyomo/core/base/objective.py | 16 +++++++--------- pyomo/core/tests/unit/test_dict_objects.py | 4 ++-- pyomo/core/tests/unit/test_list_objects.py | 4 ++-- pyomo/repn/plugins/nl_writer.py | 6 +----- pyomo/repn/standard_repn.py | 6 +++--- 17 files changed, 42 insertions(+), 48 deletions(-) diff --git a/pyomo/contrib/appsi/base.py b/pyomo/contrib/appsi/base.py index 930ff8393e9..9d00a56e8b9 100644 --- a/pyomo/contrib/appsi/base.py +++ b/pyomo/contrib/appsi/base.py @@ -26,7 +26,7 @@ from pyomo.core.base.var import VarData, Var from pyomo.core.base.param import ParamData, Param from pyomo.core.base.block import BlockData, Block -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.common.collections import ComponentMap from .utils.get_objective import get_objective from .utils.collect_vars_and_named_exprs import collect_vars_and_named_exprs @@ -827,7 +827,7 @@ def remove_block(self, block: BlockData): pass @abc.abstractmethod - def set_objective(self, obj: GeneralObjectiveData): + def set_objective(self, obj: ObjectiveData): pass @abc.abstractmethod @@ -1050,10 +1050,10 @@ def add_sos_constraints(self, cons: List[SOSConstraintData]): self._add_sos_constraints(cons) @abc.abstractmethod - def _set_objective(self, obj: GeneralObjectiveData): + def _set_objective(self, obj: ObjectiveData): pass - def set_objective(self, obj: GeneralObjectiveData): + def set_objective(self, obj: ObjectiveData): if self._objective is not None: for v in self._vars_referenced_by_obj: self._referenced_variables[id(v)][2] = None diff --git a/pyomo/contrib/appsi/fbbt.py b/pyomo/contrib/appsi/fbbt.py index 1ebb3d40381..4b0d6d4876c 100644 --- a/pyomo/contrib/appsi/fbbt.py +++ b/pyomo/contrib/appsi/fbbt.py @@ -22,7 +22,7 @@ from pyomo.core.base.param import ParamData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.sos import SOSConstraintData -from pyomo.core.base.objective import GeneralObjectiveData, minimize, maximize +from pyomo.core.base.objective import ObjectiveData, minimize, maximize from pyomo.core.base.block import BlockData from pyomo.core.base import SymbolMap, TextLabeler from pyomo.common.errors import InfeasibleConstraintException @@ -224,13 +224,13 @@ def update_params(self): cp = self._param_map[p_id] cp.value = p.value - def set_objective(self, obj: GeneralObjectiveData): + def set_objective(self, obj: ObjectiveData): if self._symbolic_solver_labels: if self._objective is not None: self._symbol_map.removeSymbol(self._objective) super().set_objective(obj) - def _set_objective(self, obj: GeneralObjectiveData): + def _set_objective(self, obj: ObjectiveData): if obj is None: ce = cmodel.Constant(0) sense = 0 diff --git a/pyomo/contrib/appsi/solvers/cbc.py b/pyomo/contrib/appsi/solvers/cbc.py index 7db9a32764e..dffd479a5c7 100644 --- a/pyomo/contrib/appsi/solvers/cbc.py +++ b/pyomo/contrib/appsi/solvers/cbc.py @@ -30,7 +30,7 @@ from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import ParamData -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.common.timing import HierarchicalTimer from pyomo.common.tee import TeeStream import sys @@ -188,7 +188,7 @@ def remove_constraints(self, cons: List[GeneralConstraintData]): def remove_block(self, block: BlockData): self._writer.remove_block(block) - def set_objective(self, obj: GeneralObjectiveData): + def set_objective(self, obj: ObjectiveData): self._writer.set_objective(obj) def update_variables(self, variables: List[VarData]): diff --git a/pyomo/contrib/appsi/solvers/cplex.py b/pyomo/contrib/appsi/solvers/cplex.py index 0ed3495ac1c..22c11bdfbe8 100644 --- a/pyomo/contrib/appsi/solvers/cplex.py +++ b/pyomo/contrib/appsi/solvers/cplex.py @@ -26,7 +26,7 @@ from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import ParamData -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.common.timing import HierarchicalTimer import sys import time @@ -203,7 +203,7 @@ def remove_constraints(self, cons: List[GeneralConstraintData]): def remove_block(self, block: BlockData): self._writer.remove_block(block) - def set_objective(self, obj: GeneralObjectiveData): + def set_objective(self, obj: ObjectiveData): self._writer.set_objective(obj) def update_variables(self, variables: List[VarData]): diff --git a/pyomo/contrib/appsi/solvers/ipopt.py b/pyomo/contrib/appsi/solvers/ipopt.py index 5cd9a51785d..4144fbbecd9 100644 --- a/pyomo/contrib/appsi/solvers/ipopt.py +++ b/pyomo/contrib/appsi/solvers/ipopt.py @@ -32,7 +32,7 @@ from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import ParamData -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.common.timing import HierarchicalTimer from pyomo.common.tee import TeeStream import sys @@ -252,7 +252,7 @@ def remove_constraints(self, cons: List[GeneralConstraintData]): def remove_block(self, block: BlockData): self._writer.remove_block(block) - def set_objective(self, obj: GeneralObjectiveData): + def set_objective(self, obj: ObjectiveData): self._writer.set_objective(obj) def update_variables(self, variables: List[VarData]): diff --git a/pyomo/contrib/appsi/writers/lp_writer.py b/pyomo/contrib/appsi/writers/lp_writer.py index 4be2b32d83d..3a6193bd314 100644 --- a/pyomo/contrib/appsi/writers/lp_writer.py +++ b/pyomo/contrib/appsi/writers/lp_writer.py @@ -13,7 +13,7 @@ from pyomo.core.base.param import ParamData from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.block import BlockData from pyomo.repn.standard_repn import generate_standard_repn @@ -147,7 +147,7 @@ def update_params(self): cp = self._pyomo_param_to_solver_param_map[p_id] cp.value = p.value - def _set_objective(self, obj: GeneralObjectiveData): + def _set_objective(self, obj: ObjectiveData): cobj = cmodel.process_lp_objective( self._expr_types, obj, diff --git a/pyomo/contrib/appsi/writers/nl_writer.py b/pyomo/contrib/appsi/writers/nl_writer.py index 70176146a1e..754bd179497 100644 --- a/pyomo/contrib/appsi/writers/nl_writer.py +++ b/pyomo/contrib/appsi/writers/nl_writer.py @@ -13,7 +13,7 @@ from pyomo.core.base.param import ParamData from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.block import BlockData from pyomo.repn.standard_repn import generate_standard_repn @@ -180,7 +180,7 @@ def update_params(self): cp = self._pyomo_param_to_solver_param_map[p_id] cp.value = p.value - def _set_objective(self, obj: GeneralObjectiveData): + def _set_objective(self, obj: ObjectiveData): if obj is None: const = cmodel.Constant(0) lin_vars = list() diff --git a/pyomo/contrib/community_detection/detection.py b/pyomo/contrib/community_detection/detection.py index af87fa5eb8b..0e2c3912e06 100644 --- a/pyomo/contrib/community_detection/detection.py +++ b/pyomo/contrib/community_detection/detection.py @@ -31,7 +31,7 @@ Objective, ConstraintList, ) -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.core.expr.visitor import replace_expressions, identify_variables from pyomo.contrib.community_detection.community_graph import generate_model_graph from pyomo.common.dependencies import networkx as nx @@ -750,7 +750,7 @@ def generate_structured_model(self): # Check to see whether 'stored_constraint' is actually an objective (since constraints and objectives # grouped together) if self.with_objective and isinstance( - stored_constraint, (GeneralObjectiveData, Objective) + stored_constraint, (ObjectiveData, Objective) ): # If the constraint is actually an objective, we add it to the block as an objective new_objective = Objective( diff --git a/pyomo/contrib/latex_printer/latex_printer.py b/pyomo/contrib/latex_printer/latex_printer.py index e11543cb375..13f30f899e4 100644 --- a/pyomo/contrib/latex_printer/latex_printer.py +++ b/pyomo/contrib/latex_printer/latex_printer.py @@ -35,7 +35,7 @@ from pyomo.core.expr.visitor import identify_components from pyomo.core.expr.base import ExpressionBase from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData -from pyomo.core.base.objective import ScalarObjective, GeneralObjectiveData +from pyomo.core.base.objective import ScalarObjective, ObjectiveData import pyomo.core.kernel as kernel from pyomo.core.expr.template_expr import ( GetItemExpression, @@ -403,7 +403,7 @@ def __init__(self): ScalarExpression: handle_named_expression_node, kernel.expression.expression: handle_named_expression_node, kernel.expression.noclone: handle_named_expression_node, - GeneralObjectiveData: handle_named_expression_node, + ObjectiveData: handle_named_expression_node, VarData: handle_var_node, ScalarObjective: handle_named_expression_node, kernel.objective.objective: handle_named_expression_node, diff --git a/pyomo/contrib/solver/base.py b/pyomo/contrib/solver/base.py index fdc7361e6b8..c53f917bc2a 100644 --- a/pyomo/contrib/solver/base.py +++ b/pyomo/contrib/solver/base.py @@ -18,7 +18,7 @@ from pyomo.core.base.var import VarData from pyomo.core.base.param import ParamData from pyomo.core.base.block import BlockData -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.common.config import document_kwargs_from_configdict, ConfigValue from pyomo.common.errors import ApplicationError from pyomo.common.deprecation import deprecation_warning @@ -274,7 +274,7 @@ def set_instance(self, model): """ @abc.abstractmethod - def set_objective(self, obj: GeneralObjectiveData): + def set_objective(self, obj: ObjectiveData): """ Set current objective for the model """ diff --git a/pyomo/contrib/solver/persistent.py b/pyomo/contrib/solver/persistent.py index 103eb3c622f..81d0df1334f 100644 --- a/pyomo/contrib/solver/persistent.py +++ b/pyomo/contrib/solver/persistent.py @@ -16,7 +16,7 @@ from pyomo.core.base.sos import SOSConstraintData, SOSConstraint from pyomo.core.base.var import VarData from pyomo.core.base.param import ParamData, Param -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.common.collections import ComponentMap from pyomo.common.timing import HierarchicalTimer from pyomo.core.expr.numvalue import NumericConstant @@ -149,10 +149,10 @@ def add_sos_constraints(self, cons: List[SOSConstraintData]): self._add_sos_constraints(cons) @abc.abstractmethod - def _set_objective(self, obj: GeneralObjectiveData): + def _set_objective(self, obj: ObjectiveData): pass - def set_objective(self, obj: GeneralObjectiveData): + def set_objective(self, obj: ObjectiveData): if self._objective is not None: for v in self._vars_referenced_by_obj: self._referenced_variables[id(v)][2] = None diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 3dd4d47046d..380aab23cbe 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -804,7 +804,7 @@ class ComponentData(_ComponentBase): # NOTE: This constructor is in-lined in the constructors for the following # classes: BooleanVarData, ConnectorData, ConstraintData, # GeneralExpressionData, LogicalConstraintData, - # LogicalConstraintData, GeneralObjectiveData, + # LogicalConstraintData, ObjectiveData, # ParamData,VarData, BooleanVarData, DisjunctionData, # ArcData, PortData, _LinearConstraintData, and # _LinearMatrixConstraintData. Changes made here need to be made in those diff --git a/pyomo/core/base/objective.py b/pyomo/core/base/objective.py index e4956748b6c..fea356229fb 100644 --- a/pyomo/core/base/objective.py +++ b/pyomo/core/base/objective.py @@ -81,9 +81,7 @@ def O_rule(model, i, j): return rule_wrapper(rule, {None: ObjectiveList.End}) -class ObjectiveData( - GeneralExpressionDataImpl, ActiveComponentData -): +class ObjectiveData(GeneralExpressionDataImpl, ActiveComponentData): """ This class defines the data for a single objective. @@ -216,7 +214,7 @@ class Objective(ActiveIndexedComponent): The class type for the derived subclass """ - _ComponentDataClass = GeneralObjectiveData + _ComponentDataClass = ObjectiveData NoObjective = ActiveIndexedComponent.Skip def __new__(cls, *args, **kwds): @@ -365,14 +363,14 @@ def display(self, prefix="", ostream=None): ) -class ScalarObjective(GeneralObjectiveData, Objective): +class ScalarObjective(ObjectiveData, Objective): """ ScalarObjective is the implementation representing a single, non-indexed objective. """ def __init__(self, *args, **kwd): - GeneralObjectiveData.__init__(self, expr=None, component=self) + ObjectiveData.__init__(self, expr=None, component=self) Objective.__init__(self, *args, **kwd) self._index = UnindexedComponent_index @@ -408,7 +406,7 @@ def expr(self): "a sense or expression (there is currently " "no value to return)." % (self.name) ) - return GeneralObjectiveData.expr.fget(self) + return ObjectiveData.expr.fget(self) raise ValueError( "Accessing the expression of objective '%s' " "before the Objective has been constructed (there " @@ -431,7 +429,7 @@ def sense(self): "a sense or expression (there is currently " "no value to return)." % (self.name) ) - return GeneralObjectiveData.sense.fget(self) + return ObjectiveData.sense.fget(self) raise ValueError( "Accessing the sense of objective '%s' " "before the Objective has been constructed (there " @@ -474,7 +472,7 @@ def set_sense(self, sense): if self._constructed: if len(self._data) == 0: self._data[None] = self - return GeneralObjectiveData.set_sense(self, sense) + return ObjectiveData.set_sense(self, sense) raise ValueError( "Setting the sense of objective '%s' " "before the Objective has been constructed (there " diff --git a/pyomo/core/tests/unit/test_dict_objects.py b/pyomo/core/tests/unit/test_dict_objects.py index 0dc5cacd216..fae1d21a87e 100644 --- a/pyomo/core/tests/unit/test_dict_objects.py +++ b/pyomo/core/tests/unit/test_dict_objects.py @@ -19,7 +19,7 @@ ) from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.core.base.expression import GeneralExpressionData @@ -384,7 +384,7 @@ def setUp(self): class TestObjectiveDict(_TestActiveComponentDictBase, unittest.TestCase): _ctype = ObjectiveDict - _cdatatype = GeneralObjectiveData + _cdatatype = ObjectiveData def setUp(self): _TestComponentDictBase.setUp(self) diff --git a/pyomo/core/tests/unit/test_list_objects.py b/pyomo/core/tests/unit/test_list_objects.py index f98b5279fc5..32f2fa328cf 100644 --- a/pyomo/core/tests/unit/test_list_objects.py +++ b/pyomo/core/tests/unit/test_list_objects.py @@ -19,7 +19,7 @@ ) from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData -from pyomo.core.base.objective import GeneralObjectiveData +from pyomo.core.base.objective import ObjectiveData from pyomo.core.base.expression import GeneralExpressionData @@ -401,7 +401,7 @@ def setUp(self): class TestObjectiveList(_TestActiveComponentListBase, unittest.TestCase): _ctype = XObjectiveList - _cdatatype = GeneralObjectiveData + _cdatatype = ObjectiveData def setUp(self): _TestComponentListBase.setUp(self) diff --git a/pyomo/repn/plugins/nl_writer.py b/pyomo/repn/plugins/nl_writer.py index 23e14104b89..3c3c8539294 100644 --- a/pyomo/repn/plugins/nl_writer.py +++ b/pyomo/repn/plugins/nl_writer.py @@ -71,11 +71,7 @@ from pyomo.core.base.component import ActiveComponent from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData -from pyomo.core.base.objective import ( - ScalarObjective, - GeneralObjectiveData, - ObjectiveData, -) +from pyomo.core.base.objective import ScalarObjective, ObjectiveData from pyomo.core.base.suffix import SuffixFinder from pyomo.core.base.var import VarData import pyomo.core.kernel as kernel diff --git a/pyomo/repn/standard_repn.py b/pyomo/repn/standard_repn.py index 2f5a413e963..a23ebf6bb4f 100644 --- a/pyomo/repn/standard_repn.py +++ b/pyomo/repn/standard_repn.py @@ -19,7 +19,7 @@ import pyomo.core.expr as EXPR from pyomo.core.expr.numvalue import NumericConstant -from pyomo.core.base.objective import GeneralObjectiveData, ScalarObjective +from pyomo.core.base.objective import ObjectiveData, ScalarObjective from pyomo.core.base import ExpressionData, Expression from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData from pyomo.core.base.var import ScalarVar, Var, VarData, value @@ -1154,7 +1154,7 @@ def _collect_external_fn(exp, multiplier, idMap, compute_values, verbose, quadra noclone: _collect_identity, ExpressionData: _collect_identity, Expression: _collect_identity, - GeneralObjectiveData: _collect_identity, + ObjectiveData: _collect_identity, ScalarObjective: _collect_identity, objective: _collect_identity, } @@ -1553,7 +1553,7 @@ def _linear_collect_pow(exp, multiplier, idMap, compute_values, verbose, coef): noclone : _linear_collect_identity, ExpressionData : _linear_collect_identity, Expression : _linear_collect_identity, - GeneralObjectiveData : _linear_collect_identity, + ObjectiveData : _linear_collect_identity, ScalarObjective : _linear_collect_identity, objective : _linear_collect_identity, } From 787eaf02a59cacd723c866c8f67740a82888c14b Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 22:38:41 -0600 Subject: [PATCH 41/83] Rename _ExpressionData, _GeneralExpressionDataImpl -> NamedExpressionData; _GeneralExpressionData -> ExpressionData --- pyomo/core/base/expression.py | 119 ++++++++++++---------------------- 1 file changed, 41 insertions(+), 78 deletions(-) diff --git a/pyomo/core/base/expression.py b/pyomo/core/base/expression.py index f5376381b2d..31bb5f835df 100644 --- a/pyomo/core/base/expression.py +++ b/pyomo/core/base/expression.py @@ -36,7 +36,7 @@ logger = logging.getLogger('pyomo.core') -class ExpressionData(numeric_expr.NumericValue): +class NamedExpressionData(numeric_expr.NumericValue): """ An object that defines a named expression. @@ -44,15 +44,14 @@ class ExpressionData(numeric_expr.NumericValue): expr The expression owned by this data. """ - __slots__ = () + __slots__ = ('_args_',) EXPRESSION_SYSTEM = EXPR.ExpressionType.NUMERIC PRECEDENCE = 0 ASSOCIATIVITY = EXPR.OperatorAssociativity.NON_ASSOCIATIVE - # - # Interface - # + def __init__(self, expr=None): + self._args_ = (expr,) def __call__(self, exception=True): """Compute the value of this expression.""" @@ -62,6 +61,18 @@ def __call__(self, exception=True): return arg return arg(exception=exception) + def create_node_with_local_data(self, values): + """ + Construct a simple expression after constructing the + contained expression. + + This class provides a consistent interface for constructing a + node, which is used in tree visitor scripts. + """ + obj = self.__class__() + obj._args_ = values + return obj + def is_named_expression_type(self): """A boolean indicating whether this in a named expression.""" return True @@ -110,9 +121,10 @@ def _compute_polynomial_degree(self, result): def _is_fixed(self, values): return values[0] - # - # Abstract Interface - # + # NamedExpressionData should never return False because + # they can store subexpressions that contain variables + def is_potentially_variable(self): + return True @property def expr(self): @@ -125,63 +137,6 @@ def expr(self): def expr(self, value): self.set_value(value) - def set_value(self, expr): - """Set the expression on this expression.""" - raise NotImplementedError - - def is_constant(self): - """A boolean indicating whether this expression is constant.""" - raise NotImplementedError - - def is_fixed(self): - """A boolean indicating whether this expression is fixed.""" - raise NotImplementedError - - # ExpressionData should never return False because - # they can store subexpressions that contain variables - def is_potentially_variable(self): - return True - - -class _ExpressionData(metaclass=RenamedClass): - __renamed__new_class__ = ExpressionData - __renamed__version__ = '6.7.2.dev0' - - -class GeneralExpressionDataImpl(ExpressionData): - """ - An object that defines an expression that is never cloned - - Constructor Arguments - expr The Pyomo expression stored in this expression. - component The Expression object that owns this data. - - Public Class Attributes - expr The expression owned by this data. - """ - - __slots__ = () - - def __init__(self, expr=None): - self._args_ = (expr,) - - def create_node_with_local_data(self, values): - """ - Construct a simple expression after constructing the - contained expression. - - This class provides a consistent interface for constructing a - node, which is used in tree visitor scripts. - """ - obj = ScalarExpression() - obj.construct() - obj._args_ = values - return obj - - # - # Abstract Interface - # - def set_value(self, expr): """Set the expression on this expression.""" if expr is None or expr.__class__ in native_numeric_types: @@ -240,7 +195,16 @@ def __ipow__(self, other): return numeric_expr._pow_dispatcher[e.__class__, other.__class__](e, other) -class GeneralExpressionData(GeneralExpressionDataImpl, ComponentData): +class _ExpressionData(metaclass=RenamedClass): + __renamed__new_class__ = NamedExpressionData + __renamed__version__ = '6.7.2.dev0' + +class _GeneralExpressionDataImpl(metaclass=RenamedClass): + __renamed__new_class__ = NamedExpressionData + __renamed__version__ = '6.7.2.dev0' + + +class ExpressionData(NamedExpressionData, ComponentData): """ An object that defines an expression that is never cloned @@ -255,17 +219,16 @@ class GeneralExpressionData(GeneralExpressionDataImpl, ComponentData): _component The expression component. """ - __slots__ = ('_args_',) + __slots__ = () def __init__(self, expr=None, component=None): - GeneralExpressionDataImpl.__init__(self, expr) - # Inlining ComponentData.__init__ + self._args_ = (expr,) self._component = weakref_ref(component) if (component is not None) else None self._index = NOTSET class _GeneralExpressionData(metaclass=RenamedClass): - __renamed__new_class__ = GeneralExpressionData + __renamed__new_class__ = ExpressionData __renamed__version__ = '6.7.2.dev0' @@ -285,7 +248,7 @@ class Expression(IndexedComponent): doc Text describing this component. """ - _ComponentDataClass = GeneralExpressionData + _ComponentDataClass = ExpressionData # This seems like a copy-paste error, and should be renamed/removed NoConstraint = IndexedComponent.Skip @@ -412,9 +375,9 @@ def construct(self, data=None): timer.report() -class ScalarExpression(GeneralExpressionData, Expression): +class ScalarExpression(ExpressionData, Expression): def __init__(self, *args, **kwds): - GeneralExpressionData.__init__(self, expr=None, component=self) + ExpressionData.__init__(self, expr=None, component=self) Expression.__init__(self, *args, **kwds) self._index = UnindexedComponent_index @@ -437,7 +400,7 @@ def __call__(self, exception=True): def expr(self): """Return expression on this expression.""" if self._constructed: - return GeneralExpressionData.expr.fget(self) + return ExpressionData.expr.fget(self) raise ValueError( "Accessing the expression of Expression '%s' " "before the Expression has been constructed (there " @@ -455,7 +418,7 @@ def clear(self): def set_value(self, expr): """Set the expression on this expression.""" if self._constructed: - return GeneralExpressionData.set_value(self, expr) + return ExpressionData.set_value(self, expr) raise ValueError( "Setting the expression of Expression '%s' " "before the Expression has been constructed (there " @@ -465,7 +428,7 @@ def set_value(self, expr): def is_constant(self): """A boolean indicating whether this expression is constant.""" if self._constructed: - return GeneralExpressionData.is_constant(self) + return ExpressionData.is_constant(self) raise ValueError( "Accessing the is_constant flag of Expression '%s' " "before the Expression has been constructed (there " @@ -475,7 +438,7 @@ def is_constant(self): def is_fixed(self): """A boolean indicating whether this expression is fixed.""" if self._constructed: - return GeneralExpressionData.is_fixed(self) + return ExpressionData.is_fixed(self) raise ValueError( "Accessing the is_fixed flag of Expression '%s' " "before the Expression has been constructed (there " @@ -519,6 +482,6 @@ def add(self, index, expr): """Add an expression with a given index.""" if (type(expr) is tuple) and (expr == Expression.Skip): return None - cdata = GeneralExpressionData(expr, component=self) + cdata = ExpressionData(expr, component=self) self._data[index] = cdata return cdata From 74b79181869619d68778eb9361d431dad362361c Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 22:40:12 -0600 Subject: [PATCH 42/83] Update *ExpressionData* referencces --- pyomo/contrib/appsi/cmodel/src/expression.hpp | 6 ++--- pyomo/contrib/cp/repn/docplex_writer.py | 6 ++--- .../logical_to_disjunctive_walker.py | 4 ++-- pyomo/contrib/fbbt/fbbt.py | 24 ++++++++----------- pyomo/contrib/latex_printer/latex_printer.py | 4 ++-- pyomo/contrib/mcpp/pyomo_mcpp.py | 6 +++-- pyomo/core/base/__init__.py | 6 +++-- pyomo/core/base/component.py | 2 +- pyomo/core/base/expression.py | 9 ++++--- pyomo/core/base/objective.py | 9 +++---- pyomo/core/expr/numeric_expr.py | 2 +- pyomo/core/tests/unit/test_dict_objects.py | 4 ++-- pyomo/core/tests/unit/test_expression.py | 8 +++---- pyomo/core/tests/unit/test_list_objects.py | 4 ++-- pyomo/dae/integral.py | 4 ++-- pyomo/gdp/tests/test_util.py | 6 ++--- pyomo/repn/plugins/ampl/ampl_.py | 4 ++-- pyomo/repn/plugins/nl_writer.py | 2 +- pyomo/repn/standard_repn.py | 16 ++++++++----- pyomo/repn/util.py | 4 ++-- 20 files changed, 67 insertions(+), 63 deletions(-) diff --git a/pyomo/contrib/appsi/cmodel/src/expression.hpp b/pyomo/contrib/appsi/cmodel/src/expression.hpp index 803bb21b6e2..ad1234b3863 100644 --- a/pyomo/contrib/appsi/cmodel/src/expression.hpp +++ b/pyomo/contrib/appsi/cmodel/src/expression.hpp @@ -700,7 +700,7 @@ class PyomoExprTypes { expr_type_map[UnaryFunctionExpression] = unary_func; expr_type_map[NPV_UnaryFunctionExpression] = unary_func; expr_type_map[LinearExpression] = linear; - expr_type_map[_GeneralExpressionData] = named_expr; + expr_type_map[_ExpressionData] = named_expr; expr_type_map[ScalarExpression] = named_expr; expr_type_map[Integral] = named_expr; expr_type_map[ScalarIntegral] = named_expr; @@ -765,8 +765,8 @@ class PyomoExprTypes { py::object NumericConstant = py::module_::import("pyomo.core.expr.numvalue").attr("NumericConstant"); py::object expr_module = py::module_::import("pyomo.core.base.expression"); - py::object _GeneralExpressionData = - expr_module.attr("_GeneralExpressionData"); + py::object _ExpressionData = + expr_module.attr("_ExpressionData"); py::object ScalarExpression = expr_module.attr("ScalarExpression"); py::object ScalarIntegral = py::module_::import("pyomo.dae.integral").attr("ScalarIntegral"); diff --git a/pyomo/contrib/cp/repn/docplex_writer.py b/pyomo/contrib/cp/repn/docplex_writer.py index 1af153910c0..37429d420d2 100644 --- a/pyomo/contrib/cp/repn/docplex_writer.py +++ b/pyomo/contrib/cp/repn/docplex_writer.py @@ -63,7 +63,7 @@ BooleanVarData, IndexedBooleanVar, ) -from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData +from pyomo.core.base.expression import ScalarExpression, ExpressionData from pyomo.core.base.param import IndexedParam, ScalarParam, ParamData from pyomo.core.base.var import ScalarVar, VarData, IndexedVar import pyomo.core.expr as EXPR @@ -949,7 +949,7 @@ class LogicalToDoCplex(StreamBasedExpressionVisitor): BeforeExpression: _handle_before_expression_node, AtExpression: _handle_at_expression_node, AlwaysIn: _handle_always_in_node, - GeneralExpressionData: _handle_named_expression_node, + ExpressionData: _handle_named_expression_node, ScalarExpression: _handle_named_expression_node, } _var_handles = { @@ -966,7 +966,7 @@ class LogicalToDoCplex(StreamBasedExpressionVisitor): ScalarBooleanVar: _before_boolean_var, BooleanVarData: _before_boolean_var, IndexedBooleanVar: _before_indexed_boolean_var, - GeneralExpressionData: _before_named_expression, + ExpressionData: _before_named_expression, ScalarExpression: _before_named_expression, IndexedParam: _before_indexed_param, # Because of indirection ScalarParam: _before_param, diff --git a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py index 0c493b89321..fdcfd5a8308 100644 --- a/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py +++ b/pyomo/contrib/cp/transform/logical_to_disjunctive_walker.py @@ -27,7 +27,7 @@ value, ) import pyomo.core.base.boolean_var as BV -from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData +from pyomo.core.base.expression import ScalarExpression, ExpressionData from pyomo.core.base.param import ScalarParam, ParamData from pyomo.core.base.var import ScalarVar, VarData from pyomo.gdp.disjunct import AutoLinkedBooleanVar, Disjunct, Disjunction @@ -217,7 +217,7 @@ def _dispatch_atmost(visitor, node, *args): # don't handle them: _before_child_dispatcher[ScalarVar] = _dispatch_var _before_child_dispatcher[VarData] = _dispatch_var -_before_child_dispatcher[GeneralExpressionData] = _dispatch_expression +_before_child_dispatcher[ExpressionData] = _dispatch_expression _before_child_dispatcher[ScalarExpression] = _dispatch_expression diff --git a/pyomo/contrib/fbbt/fbbt.py b/pyomo/contrib/fbbt/fbbt.py index 86f94506841..eb7155313c4 100644 --- a/pyomo/contrib/fbbt/fbbt.py +++ b/pyomo/contrib/fbbt/fbbt.py @@ -26,7 +26,7 @@ from pyomo.core.base.constraint import Constraint from pyomo.core.base.var import Var from pyomo.gdp import Disjunct -from pyomo.core.base.expression import GeneralExpressionData, ScalarExpression +from pyomo.core.base.expression import ExpressionData, ScalarExpression import logging from pyomo.common.errors import InfeasibleConstraintException, PyomoException from pyomo.common.config import ( @@ -333,15 +333,15 @@ def _prop_bnds_leaf_to_root_UnaryFunctionExpression(visitor, node, arg): _unary_leaf_to_root_map[node.getname()](visitor, node, arg) -def _prop_bnds_leaf_to_root_GeneralExpression(visitor, node, expr): +def _prop_bnds_leaf_to_root_NamedExpression(visitor, node, expr): """ Propagate bounds from children to parent Parameters ---------- visitor: _FBBTVisitorLeafToRoot - node: pyomo.core.base.expression.GeneralExpressionData - expr: GeneralExpression arg + node: pyomo.core.base.expression.ExpressionData + expr: NamedExpressionData arg """ bnds_dict = visitor.bnds_dict if node in bnds_dict: @@ -366,8 +366,8 @@ def _prop_bnds_leaf_to_root_GeneralExpression(visitor, node, expr): numeric_expr.UnaryFunctionExpression: _prop_bnds_leaf_to_root_UnaryFunctionExpression, numeric_expr.LinearExpression: _prop_bnds_leaf_to_root_SumExpression, numeric_expr.AbsExpression: _prop_bnds_leaf_to_root_abs, - GeneralExpressionData: _prop_bnds_leaf_to_root_GeneralExpression, - ScalarExpression: _prop_bnds_leaf_to_root_GeneralExpression, + ExpressionData: _prop_bnds_leaf_to_root_NamedExpression, + ScalarExpression: _prop_bnds_leaf_to_root_NamedExpression, }, ) @@ -898,13 +898,13 @@ def _prop_bnds_root_to_leaf_UnaryFunctionExpression(node, bnds_dict, feasibility ) -def _prop_bnds_root_to_leaf_GeneralExpression(node, bnds_dict, feasibility_tol): +def _prop_bnds_root_to_leaf_NamedExpression(node, bnds_dict, feasibility_tol): """ Propagate bounds from parent to children. Parameters ---------- - node: pyomo.core.base.expression.GeneralExpressionData + node: pyomo.core.base.expression.ExpressionData bnds_dict: ComponentMap feasibility_tol: float If the bounds computed on the body of a constraint violate the bounds of the constraint by more than @@ -945,12 +945,8 @@ def _prop_bnds_root_to_leaf_GeneralExpression(node, bnds_dict, feasibility_tol): ) _prop_bnds_root_to_leaf_map[numeric_expr.AbsExpression] = _prop_bnds_root_to_leaf_abs -_prop_bnds_root_to_leaf_map[GeneralExpressionData] = ( - _prop_bnds_root_to_leaf_GeneralExpression -) -_prop_bnds_root_to_leaf_map[ScalarExpression] = ( - _prop_bnds_root_to_leaf_GeneralExpression -) +_prop_bnds_root_to_leaf_map[ExpressionData] = _prop_bnds_root_to_leaf_NamedExpression +_prop_bnds_root_to_leaf_map[ScalarExpression] = _prop_bnds_root_to_leaf_NamedExpression def _check_and_reset_bounds(var, lb, ub): diff --git a/pyomo/contrib/latex_printer/latex_printer.py b/pyomo/contrib/latex_printer/latex_printer.py index 13f30f899e4..cf286472a66 100644 --- a/pyomo/contrib/latex_printer/latex_printer.py +++ b/pyomo/contrib/latex_printer/latex_printer.py @@ -34,7 +34,7 @@ from pyomo.core.expr.visitor import identify_components from pyomo.core.expr.base import ExpressionBase -from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData +from pyomo.core.base.expression import ScalarExpression, ExpressionData from pyomo.core.base.objective import ScalarObjective, ObjectiveData import pyomo.core.kernel as kernel from pyomo.core.expr.template_expr import ( @@ -399,7 +399,7 @@ def __init__(self): EqualityExpression: handle_equality_node, InequalityExpression: handle_inequality_node, RangedExpression: handle_ranged_inequality_node, - GeneralExpressionData: handle_named_expression_node, + ExpressionData: handle_named_expression_node, ScalarExpression: handle_named_expression_node, kernel.expression.expression: handle_named_expression_node, kernel.expression.noclone: handle_named_expression_node, diff --git a/pyomo/contrib/mcpp/pyomo_mcpp.py b/pyomo/contrib/mcpp/pyomo_mcpp.py index 1375ae61c50..0ef0237681b 100644 --- a/pyomo/contrib/mcpp/pyomo_mcpp.py +++ b/pyomo/contrib/mcpp/pyomo_mcpp.py @@ -20,7 +20,7 @@ from pyomo.common.fileutils import Library from pyomo.core import value, Expression from pyomo.core.base.block import SubclassOf -from pyomo.core.base.expression import ExpressionData +from pyomo.core.base.expression import NamedExpressionData from pyomo.core.expr.numvalue import nonpyomo_leaf_types from pyomo.core.expr.numeric_expr import ( AbsExpression, @@ -307,7 +307,9 @@ def exitNode(self, node, data): ans = self.mcpp.newConstant(node) elif not node.is_expression_type(): ans = self.register_num(node) - elif type(node) in SubclassOf(Expression) or isinstance(node, ExpressionData): + elif type(node) in SubclassOf(Expression) or isinstance( + node, NamedExpressionData + ): ans = data[0] else: raise RuntimeError("Unhandled expression type: %s" % (type(node))) diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index bcc2a0e0e02..3d1347659db 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -97,7 +97,7 @@ Constraint, ConstraintData, ) -from pyomo.core.base.expression import Expression, ExpressionData +from pyomo.core.base.expression import Expression, NamedExpressionData, ExpressionData from pyomo.core.base.external import ExternalFunction from pyomo.core.base.logical_constraint import ( LogicalConstraint, @@ -170,10 +170,12 @@ relocated_module_attribute( f'_GeneralBooleanVarData', f'pyomo.core.base.BooleanVarData', version='6.7.2.dev0' ) +relocated_module_attribute( + f'_ExpressionData', f'pyomo.core.base.NamedExpressionData', version='6.7.2.dev0' +) for _cdata in ( 'ConstraintData', 'LogicalConstraintData', - 'ExpressionData', 'VarData', 'BooleanVarData', 'ObjectiveData', diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 380aab23cbe..50cf264c799 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -803,7 +803,7 @@ class ComponentData(_ComponentBase): # NOTE: This constructor is in-lined in the constructors for the following # classes: BooleanVarData, ConnectorData, ConstraintData, - # GeneralExpressionData, LogicalConstraintData, + # ExpressionData, LogicalConstraintData, # LogicalConstraintData, ObjectiveData, # ParamData,VarData, BooleanVarData, DisjunctionData, # ArcData, PortData, _LinearConstraintData, and diff --git a/pyomo/core/base/expression.py b/pyomo/core/base/expression.py index 31bb5f835df..10720366e28 100644 --- a/pyomo/core/base/expression.py +++ b/pyomo/core/base/expression.py @@ -44,15 +44,13 @@ class NamedExpressionData(numeric_expr.NumericValue): expr The expression owned by this data. """ - __slots__ = ('_args_',) + # Note: derived classes are expected to declare teh _args_ slot + __slots__ = () EXPRESSION_SYSTEM = EXPR.ExpressionType.NUMERIC PRECEDENCE = 0 ASSOCIATIVITY = EXPR.OperatorAssociativity.NON_ASSOCIATIVE - def __init__(self, expr=None): - self._args_ = (expr,) - def __call__(self, exception=True): """Compute the value of this expression.""" (arg,) = self._args_ @@ -199,6 +197,7 @@ class _ExpressionData(metaclass=RenamedClass): __renamed__new_class__ = NamedExpressionData __renamed__version__ = '6.7.2.dev0' + class _GeneralExpressionDataImpl(metaclass=RenamedClass): __renamed__new_class__ = NamedExpressionData __renamed__version__ = '6.7.2.dev0' @@ -219,7 +218,7 @@ class ExpressionData(NamedExpressionData, ComponentData): _component The expression component. """ - __slots__ = () + __slots__ = ('_args_',) def __init__(self, expr=None, component=None): self._args_ = (expr,) diff --git a/pyomo/core/base/objective.py b/pyomo/core/base/objective.py index fea356229fb..71cf5ba78f8 100644 --- a/pyomo/core/base/objective.py +++ b/pyomo/core/base/objective.py @@ -28,7 +28,7 @@ UnindexedComponent_set, rule_wrapper, ) -from pyomo.core.base.expression import ExpressionData, GeneralExpressionDataImpl +from pyomo.core.base.expression import NamedExpressionData from pyomo.core.base.set import Set from pyomo.core.base.initializer import ( Initializer, @@ -81,7 +81,7 @@ def O_rule(model, i, j): return rule_wrapper(rule, {None: ObjectiveList.End}) -class ObjectiveData(GeneralExpressionDataImpl, ActiveComponentData): +class ObjectiveData(NamedExpressionData, ActiveComponentData): """ This class defines the data for a single objective. @@ -104,10 +104,11 @@ class ObjectiveData(GeneralExpressionDataImpl, ActiveComponentData): _active A boolean that indicates whether this data is active """ - __slots__ = ("_sense", "_args_") + __slots__ = ("_args_", "_sense") def __init__(self, expr=None, sense=minimize, component=None): - GeneralExpressionDataImpl.__init__(self, expr) + # Inlining NamedExpressionData.__init__ + self._args_ = (expr,) # Inlining ActiveComponentData.__init__ self._component = weakref_ref(component) if (component is not None) else None self._index = NOTSET diff --git a/pyomo/core/expr/numeric_expr.py b/pyomo/core/expr/numeric_expr.py index 50abaeedbba..49bb2e0280f 100644 --- a/pyomo/core/expr/numeric_expr.py +++ b/pyomo/core/expr/numeric_expr.py @@ -722,7 +722,7 @@ def args(self): @deprecated( 'The implicit recasting of a "not potentially variable" ' 'expression node to a potentially variable one is no ' - 'longer supported (this violates that immutability ' + 'longer supported (this violates the immutability ' 'promise for Pyomo5 expression trees).', version='6.4.3', ) diff --git a/pyomo/core/tests/unit/test_dict_objects.py b/pyomo/core/tests/unit/test_dict_objects.py index fae1d21a87e..16b7e0bd2e0 100644 --- a/pyomo/core/tests/unit/test_dict_objects.py +++ b/pyomo/core/tests/unit/test_dict_objects.py @@ -20,7 +20,7 @@ from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import ObjectiveData -from pyomo.core.base.expression import GeneralExpressionData +from pyomo.core.base.expression import ExpressionData class _TestComponentDictBase(object): @@ -360,7 +360,7 @@ def setUp(self): class TestExpressionDict(_TestComponentDictBase, unittest.TestCase): _ctype = ExpressionDict - _cdatatype = GeneralExpressionData + _cdatatype = ExpressionData def setUp(self): _TestComponentDictBase.setUp(self) diff --git a/pyomo/core/tests/unit/test_expression.py b/pyomo/core/tests/unit/test_expression.py index bf3ce0c2179..eb16f7c6142 100644 --- a/pyomo/core/tests/unit/test_expression.py +++ b/pyomo/core/tests/unit/test_expression.py @@ -29,7 +29,7 @@ value, sum_product, ) -from pyomo.core.base.expression import GeneralExpressionData +from pyomo.core.base.expression import ExpressionData from pyomo.core.expr.compare import compare_expressions, assertExpressionsEqual from pyomo.common.tee import capture_output @@ -515,10 +515,10 @@ def test_implicit_definition(self): model.E = Expression(model.idx) self.assertEqual(len(model.E), 3) expr = model.E[1] - self.assertIs(type(expr), GeneralExpressionData) + self.assertIs(type(expr), ExpressionData) model.E[1] = None self.assertIs(expr, model.E[1]) - self.assertIs(type(expr), GeneralExpressionData) + self.assertIs(type(expr), ExpressionData) self.assertIs(expr.expr, None) model.E[1] = 5 self.assertIs(expr, model.E[1]) @@ -537,7 +537,7 @@ def test_explicit_skip_definition(self): model.E[1] = None expr = model.E[1] - self.assertIs(type(expr), GeneralExpressionData) + self.assertIs(type(expr), ExpressionData) self.assertIs(expr.expr, None) model.E[1] = 5 self.assertIs(expr, model.E[1]) diff --git a/pyomo/core/tests/unit/test_list_objects.py b/pyomo/core/tests/unit/test_list_objects.py index 32f2fa328cf..94913bcbc02 100644 --- a/pyomo/core/tests/unit/test_list_objects.py +++ b/pyomo/core/tests/unit/test_list_objects.py @@ -20,7 +20,7 @@ from pyomo.core.base.var import VarData from pyomo.core.base.constraint import GeneralConstraintData from pyomo.core.base.objective import ObjectiveData -from pyomo.core.base.expression import GeneralExpressionData +from pyomo.core.base.expression import ExpressionData class _TestComponentListBase(object): @@ -377,7 +377,7 @@ def setUp(self): class TestExpressionList(_TestComponentListBase, unittest.TestCase): _ctype = XExpressionList - _cdatatype = GeneralExpressionData + _cdatatype = ExpressionData def setUp(self): _TestComponentListBase.setUp(self) diff --git a/pyomo/dae/integral.py b/pyomo/dae/integral.py index f767e31f18c..8c9512d98dd 100644 --- a/pyomo/dae/integral.py +++ b/pyomo/dae/integral.py @@ -14,7 +14,7 @@ from pyomo.core.base.indexed_component import rule_wrapper from pyomo.core.base.expression import ( Expression, - GeneralExpressionData, + ExpressionData, ScalarExpression, IndexedExpression, ) @@ -151,7 +151,7 @@ class ScalarIntegral(ScalarExpression, Integral): """ def __init__(self, *args, **kwds): - GeneralExpressionData.__init__(self, None, component=self) + ExpressionData.__init__(self, None, component=self) Integral.__init__(self, *args, **kwds) def clear(self): diff --git a/pyomo/gdp/tests/test_util.py b/pyomo/gdp/tests/test_util.py index 8ea72af37da..fa8e953f9f7 100644 --- a/pyomo/gdp/tests/test_util.py +++ b/pyomo/gdp/tests/test_util.py @@ -13,7 +13,7 @@ from pyomo.core import ConcreteModel, Var, Expression, Block, RangeSet, Any import pyomo.core.expr as EXPR -from pyomo.core.base.expression import ExpressionData +from pyomo.core.base.expression import NamedExpressionData from pyomo.gdp.util import ( clone_without_expression_components, is_child_of, @@ -40,7 +40,7 @@ def test_clone_without_expression_components(self): test = clone_without_expression_components(base, {}) self.assertIsNot(base, test) self.assertEqual(base(), test()) - self.assertIsInstance(base, ExpressionData) + self.assertIsInstance(base, NamedExpressionData) self.assertIsInstance(test, EXPR.SumExpression) test = clone_without_expression_components(base, {id(m.x): m.y}) self.assertEqual(3**2 + 3 - 1, test()) @@ -51,7 +51,7 @@ def test_clone_without_expression_components(self): self.assertEqual(base(), test()) self.assertIsInstance(base, EXPR.SumExpression) self.assertIsInstance(test, EXPR.SumExpression) - self.assertIsInstance(base.arg(0), ExpressionData) + self.assertIsInstance(base.arg(0), NamedExpressionData) self.assertIsInstance(test.arg(0), EXPR.SumExpression) test = clone_without_expression_components(base, {id(m.x): m.y}) self.assertEqual(3**2 + 3 - 1 + 3, test()) diff --git a/pyomo/repn/plugins/ampl/ampl_.py b/pyomo/repn/plugins/ampl/ampl_.py index 1cff45b30c1..cc99e9cfdae 100644 --- a/pyomo/repn/plugins/ampl/ampl_.py +++ b/pyomo/repn/plugins/ampl/ampl_.py @@ -33,7 +33,7 @@ from pyomo.core.base import ( SymbolMap, NameLabeler, - ExpressionData, + NamedExpressionData, SortComponents, var, param, @@ -724,7 +724,7 @@ def _print_nonlinear_terms_NL(self, exp): self._print_nonlinear_terms_NL(exp.arg(0)) self._print_nonlinear_terms_NL(exp.arg(1)) - elif isinstance(exp, (ExpressionData, IIdentityExpression)): + elif isinstance(exp, (NamedExpressionData, IIdentityExpression)): self._print_nonlinear_terms_NL(exp.expr) else: diff --git a/pyomo/repn/plugins/nl_writer.py b/pyomo/repn/plugins/nl_writer.py index 3c3c8539294..8cc73b5e3fe 100644 --- a/pyomo/repn/plugins/nl_writer.py +++ b/pyomo/repn/plugins/nl_writer.py @@ -70,7 +70,7 @@ ) from pyomo.core.base.component import ActiveComponent from pyomo.core.base.constraint import ConstraintData -from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData +from pyomo.core.base.expression import ScalarExpression, ExpressionData from pyomo.core.base.objective import ScalarObjective, ObjectiveData from pyomo.core.base.suffix import SuffixFinder from pyomo.core.base.var import VarData diff --git a/pyomo/repn/standard_repn.py b/pyomo/repn/standard_repn.py index a23ebf6bb4f..b767ab727af 100644 --- a/pyomo/repn/standard_repn.py +++ b/pyomo/repn/standard_repn.py @@ -20,8 +20,12 @@ import pyomo.core.expr as EXPR from pyomo.core.expr.numvalue import NumericConstant from pyomo.core.base.objective import ObjectiveData, ScalarObjective -from pyomo.core.base import ExpressionData, Expression -from pyomo.core.base.expression import ScalarExpression, GeneralExpressionData +from pyomo.core.base import Expression +from pyomo.core.base.expression import ( + ScalarExpression, + NamedExpressionData, + ExpressionData, +) from pyomo.core.base.var import ScalarVar, Var, VarData, value from pyomo.core.base.param import ScalarParam, ParamData from pyomo.core.kernel.expression import expression, noclone @@ -1148,11 +1152,11 @@ def _collect_external_fn(exp, multiplier, idMap, compute_values, verbose, quadra Var: _collect_var, variable: _collect_var, IVariable: _collect_var, - GeneralExpressionData: _collect_identity, + ExpressionData: _collect_identity, ScalarExpression: _collect_identity, expression: _collect_identity, noclone: _collect_identity, - ExpressionData: _collect_identity, + NamedExpressionData: _collect_identity, Expression: _collect_identity, ObjectiveData: _collect_identity, ScalarObjective: _collect_identity, @@ -1547,11 +1551,11 @@ def _linear_collect_pow(exp, multiplier, idMap, compute_values, verbose, coef): Var : _linear_collect_var, variable : _linear_collect_var, IVariable : _linear_collect_var, - GeneralExpressionData : _linear_collect_identity, + ExpressionData : _linear_collect_identity, ScalarExpression : _linear_collect_identity, expression : _linear_collect_identity, noclone : _linear_collect_identity, - ExpressionData : _linear_collect_identity, + NamedExpressionData : _linear_collect_identity, Expression : _linear_collect_identity, ObjectiveData : _linear_collect_identity, ScalarObjective : _linear_collect_identity, diff --git a/pyomo/repn/util.py b/pyomo/repn/util.py index 7351ea51c58..9a8713c6965 100644 --- a/pyomo/repn/util.py +++ b/pyomo/repn/util.py @@ -40,7 +40,7 @@ SortComponents, ) from pyomo.core.base.component import ActiveComponent -from pyomo.core.base.expression import ExpressionData +from pyomo.core.base.expression import NamedExpressionData from pyomo.core.expr.numvalue import is_fixed, value import pyomo.core.expr as EXPR import pyomo.core.kernel as kernel @@ -55,7 +55,7 @@ EXPR.NPV_SumExpression, } _named_subexpression_types = ( - ExpressionData, + NamedExpressionData, kernel.expression.expression, kernel.objective.objective, ) From 47bb04f00f591f175a7a65e656197a41fc0eae50 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 20 Mar 2024 23:29:02 -0600 Subject: [PATCH 43/83] Add missing method from GeneralLogicalConstraintData merge --- pyomo/core/base/logical_constraint.py | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/pyomo/core/base/logical_constraint.py b/pyomo/core/base/logical_constraint.py index 1daa5f83e90..9584078307d 100644 --- a/pyomo/core/base/logical_constraint.py +++ b/pyomo/core/base/logical_constraint.py @@ -77,6 +77,12 @@ def __init__(self, expr=None, component=None): if expr is not None: self.set_value(expr) + def __call__(self, exception=True): + """Compute the value of the body of this logical constraint.""" + if self.body is None: + return None + return self.body(exception=exception) + # # Abstract Interface # From d26a83ff243c7412bcb978f0f571b53ebc737f6c Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 21 Mar 2024 10:47:13 -0600 Subject: [PATCH 44/83] NFC: fix typo --- pyomo/core/base/expression.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyomo/core/base/expression.py b/pyomo/core/base/expression.py index 10720366e28..5638e48ea8b 100644 --- a/pyomo/core/base/expression.py +++ b/pyomo/core/base/expression.py @@ -44,7 +44,7 @@ class NamedExpressionData(numeric_expr.NumericValue): expr The expression owned by this data. """ - # Note: derived classes are expected to declare teh _args_ slot + # Note: derived classes are expected to declare the _args_ slot __slots__ = () EXPRESSION_SYSTEM = EXPR.ExpressionType.NUMERIC From db7b6b22ad1c2f3659fce2cb0cd96c69727ef6f3 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 21 Mar 2024 10:47:52 -0600 Subject: [PATCH 45/83] Update ComponentData references in APPSI --- pyomo/contrib/appsi/cmodel/src/expression.hpp | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/pyomo/contrib/appsi/cmodel/src/expression.hpp b/pyomo/contrib/appsi/cmodel/src/expression.hpp index ad1234b3863..e91ca0af3b3 100644 --- a/pyomo/contrib/appsi/cmodel/src/expression.hpp +++ b/pyomo/contrib/appsi/cmodel/src/expression.hpp @@ -680,10 +680,10 @@ class PyomoExprTypes { expr_type_map[np_float32] = py_float; expr_type_map[np_float64] = py_float; expr_type_map[ScalarVar] = var; - expr_type_map[_VarData] = var; + expr_type_map[VarData] = var; expr_type_map[AutoLinkedBinaryVar] = var; expr_type_map[ScalarParam] = param; - expr_type_map[_ParamData] = param; + expr_type_map[ParamData] = param; expr_type_map[MonomialTermExpression] = product; expr_type_map[ProductExpression] = product; expr_type_map[NPV_ProductExpression] = product; @@ -700,7 +700,7 @@ class PyomoExprTypes { expr_type_map[UnaryFunctionExpression] = unary_func; expr_type_map[NPV_UnaryFunctionExpression] = unary_func; expr_type_map[LinearExpression] = linear; - expr_type_map[_ExpressionData] = named_expr; + expr_type_map[ExpressionData] = named_expr; expr_type_map[ScalarExpression] = named_expr; expr_type_map[Integral] = named_expr; expr_type_map[ScalarIntegral] = named_expr; @@ -728,12 +728,12 @@ class PyomoExprTypes { py::type np_float64 = np.attr("float64"); py::object ScalarParam = py::module_::import("pyomo.core.base.param").attr("ScalarParam"); - py::object _ParamData = - py::module_::import("pyomo.core.base.param").attr("_ParamData"); + py::object ParamData = + py::module_::import("pyomo.core.base.param").attr("ParamData"); py::object ScalarVar = py::module_::import("pyomo.core.base.var").attr("ScalarVar"); - py::object _VarData = - py::module_::import("pyomo.core.base.var").attr("_VarData"); + py::object VarData = + py::module_::import("pyomo.core.base.var").attr("VarData"); py::object AutoLinkedBinaryVar = py::module_::import("pyomo.gdp.disjunct").attr("AutoLinkedBinaryVar"); py::object numeric_expr = py::module_::import("pyomo.core.expr.numeric_expr"); @@ -765,8 +765,8 @@ class PyomoExprTypes { py::object NumericConstant = py::module_::import("pyomo.core.expr.numvalue").attr("NumericConstant"); py::object expr_module = py::module_::import("pyomo.core.base.expression"); - py::object _ExpressionData = - expr_module.attr("_ExpressionData"); + py::object ExpressionData = + expr_module.attr("ExpressionData"); py::object ScalarExpression = expr_module.attr("ScalarExpression"); py::object ScalarIntegral = py::module_::import("pyomo.dae.integral").attr("ScalarIntegral"); From 5b48eb28989c29f23324d6d3e6cdf1ca452346fc Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 21 Mar 2024 12:18:53 -0600 Subject: [PATCH 46/83] Merge GeneralConstraintData into ConstraintData --- pyomo/core/base/constraint.py | 244 ++++++++++------------------------ 1 file changed, 70 insertions(+), 174 deletions(-) diff --git a/pyomo/core/base/constraint.py b/pyomo/core/base/constraint.py index 3455d2dde3c..08c97d7c8ae 100644 --- a/pyomo/core/base/constraint.py +++ b/pyomo/core/base/constraint.py @@ -125,17 +125,13 @@ def C_rule(model, i, j): return rule_wrapper(rule, result_map, map_types=map_types) -# -# This class is a pure interface -# - - -class ConstraintData(ActiveComponentData): +class ConstraintData(ConstraintData): """ - This class defines the data for a single constraint. + This class defines the data for a single general constraint. Constructor arguments: component The Constraint object that owns this data. + expr The Pyomo expression stored in this constraint. Public class attributes: active A boolean that is true if this constraint is @@ -155,164 +151,12 @@ class ConstraintData(ActiveComponentData): _active A boolean that indicates whether this data is active """ - __slots__ = () + __slots__ = ('_body', '_lower', '_upper', '_expr') # Set to true when a constraint class stores its expression # in linear canonical form _linear_canonical_form = False - def __init__(self, component=None): - # - # These lines represent in-lining of the - # following constructors: - # - ConstraintData, - # - ActiveComponentData - # - ComponentData - self._component = weakref_ref(component) if (component is not None) else None - self._index = NOTSET - self._active = True - - # - # Interface - # - - def __call__(self, exception=True): - """Compute the value of the body of this constraint.""" - return value(self.body, exception=exception) - - def has_lb(self): - """Returns :const:`False` when the lower bound is - :const:`None` or negative infinity""" - return self.lb is not None - - def has_ub(self): - """Returns :const:`False` when the upper bound is - :const:`None` or positive infinity""" - return self.ub is not None - - def lslack(self): - """ - Returns the value of f(x)-L for constraints of the form: - L <= f(x) (<= U) - (U >=) f(x) >= L - """ - lb = self.lb - if lb is None: - return _inf - else: - return value(self.body) - lb - - def uslack(self): - """ - Returns the value of U-f(x) for constraints of the form: - (L <=) f(x) <= U - U >= f(x) (>= L) - """ - ub = self.ub - if ub is None: - return _inf - else: - return ub - value(self.body) - - def slack(self): - """ - Returns the smaller of lslack and uslack values - """ - lb = self.lb - ub = self.ub - body = value(self.body) - if lb is None: - return ub - body - elif ub is None: - return body - lb - return min(ub - body, body - lb) - - # - # Abstract Interface - # - - @property - def body(self): - """Access the body of a constraint expression.""" - raise NotImplementedError - - @property - def lower(self): - """Access the lower bound of a constraint expression.""" - raise NotImplementedError - - @property - def upper(self): - """Access the upper bound of a constraint expression.""" - raise NotImplementedError - - @property - def lb(self): - """Access the value of the lower bound of a constraint expression.""" - raise NotImplementedError - - @property - def ub(self): - """Access the value of the upper bound of a constraint expression.""" - raise NotImplementedError - - @property - def equality(self): - """A boolean indicating whether this is an equality constraint.""" - raise NotImplementedError - - @property - def strict_lower(self): - """True if this constraint has a strict lower bound.""" - raise NotImplementedError - - @property - def strict_upper(self): - """True if this constraint has a strict upper bound.""" - raise NotImplementedError - - def set_value(self, expr): - """Set the expression on this constraint.""" - raise NotImplementedError - - def get_value(self): - """Get the expression on this constraint.""" - raise NotImplementedError - - -class _ConstraintData(metaclass=RenamedClass): - __renamed__new_class__ = ConstraintData - __renamed__version__ = '6.7.2.dev0' - - -class GeneralConstraintData(ConstraintData): - """ - This class defines the data for a single general constraint. - - Constructor arguments: - component The Constraint object that owns this data. - expr The Pyomo expression stored in this constraint. - - Public class attributes: - active A boolean that is true if this constraint is - active in the model. - body The Pyomo expression for this constraint - lower The Pyomo expression for the lower bound - upper The Pyomo expression for the upper bound - equality A boolean that indicates whether this is an - equality constraint - strict_lower A boolean that indicates whether this - constraint uses a strict lower bound - strict_upper A boolean that indicates whether this - constraint uses a strict upper bound - - Private class attributes: - _component The objective component. - _active A boolean that indicates whether this data is active - """ - - __slots__ = ('_body', '_lower', '_upper', '_expr') - def __init__(self, expr=None, component=None): # # These lines represent in-lining of the @@ -330,9 +174,9 @@ def __init__(self, expr=None, component=None): if expr is not None: self.set_value(expr) - # - # Abstract Interface - # + def __call__(self, exception=True): + """Compute the value of the body of this constraint.""" + return value(self.body, exception=exception) @property def body(self): @@ -456,6 +300,16 @@ def strict_upper(self): """True if this constraint has a strict upper bound.""" return False + def has_lb(self): + """Returns :const:`False` when the lower bound is + :const:`None` or negative infinity""" + return self.lb is not None + + def has_ub(self): + """Returns :const:`False` when the upper bound is + :const:`None` or positive infinity""" + return self.ub is not None + @property def expr(self): """Return the expression associated with this constraint.""" @@ -683,9 +537,51 @@ def set_value(self, expr): "upper bound (%s)." % (self.name, self._upper) ) + def lslack(self): + """ + Returns the value of f(x)-L for constraints of the form: + L <= f(x) (<= U) + (U >=) f(x) >= L + """ + lb = self.lb + if lb is None: + return _inf + else: + return value(self.body) - lb + + def uslack(self): + """ + Returns the value of U-f(x) for constraints of the form: + (L <=) f(x) <= U + U >= f(x) (>= L) + """ + ub = self.ub + if ub is None: + return _inf + else: + return ub - value(self.body) + + def slack(self): + """ + Returns the smaller of lslack and uslack values + """ + lb = self.lb + ub = self.ub + body = value(self.body) + if lb is None: + return ub - body + elif ub is None: + return body - lb + return min(ub - body, body - lb) + + +class _ConstraintData(metaclass=RenamedClass): + __renamed__new_class__ = ConstraintData + __renamed__version__ = '6.7.2.dev0' + class _GeneralConstraintData(metaclass=RenamedClass): - __renamed__new_class__ = GeneralConstraintData + __renamed__new_class__ = ConstraintData __renamed__version__ = '6.7.2.dev0' @@ -731,7 +627,7 @@ class Constraint(ActiveIndexedComponent): The class type for the derived subclass """ - _ComponentDataClass = GeneralConstraintData + _ComponentDataClass = ConstraintData class Infeasible(object): pass @@ -889,14 +785,14 @@ def display(self, prefix="", ostream=None): ) -class ScalarConstraint(GeneralConstraintData, Constraint): +class ScalarConstraint(ConstraintData, Constraint): """ ScalarConstraint is the implementation representing a single, non-indexed constraint. """ def __init__(self, *args, **kwds): - GeneralConstraintData.__init__(self, component=self, expr=None) + ConstraintData.__init__(self, component=self, expr=None) Constraint.__init__(self, *args, **kwds) self._index = UnindexedComponent_index @@ -920,7 +816,7 @@ def body(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return GeneralConstraintData.body.fget(self) + return ConstraintData.body.fget(self) @property def lower(self): @@ -932,7 +828,7 @@ def lower(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return GeneralConstraintData.lower.fget(self) + return ConstraintData.lower.fget(self) @property def upper(self): @@ -944,7 +840,7 @@ def upper(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return GeneralConstraintData.upper.fget(self) + return ConstraintData.upper.fget(self) @property def equality(self): @@ -956,7 +852,7 @@ def equality(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return GeneralConstraintData.equality.fget(self) + return ConstraintData.equality.fget(self) @property def strict_lower(self): @@ -968,7 +864,7 @@ def strict_lower(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return GeneralConstraintData.strict_lower.fget(self) + return ConstraintData.strict_lower.fget(self) @property def strict_upper(self): @@ -980,7 +876,7 @@ def strict_upper(self): "an expression. There is currently " "nothing to access." % (self.name) ) - return GeneralConstraintData.strict_upper.fget(self) + return ConstraintData.strict_upper.fget(self) def clear(self): self._data = {} @@ -1045,7 +941,7 @@ def add(self, index, expr): return self.__setitem__(index, expr) @overload - def __getitem__(self, index) -> GeneralConstraintData: ... + def __getitem__(self, index) -> ConstraintData: ... __getitem__ = IndexedComponent.__getitem__ # type: ignore From 97ad3c0945ca1426729a107320a06c21d54653c0 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 21 Mar 2024 15:15:03 -0600 Subject: [PATCH 47/83] Update references from GeneralConstraintData to ConstraintData --- pyomo/contrib/appsi/base.py | 48 +++++++++---------- pyomo/contrib/appsi/fbbt.py | 6 +-- pyomo/contrib/appsi/solvers/cbc.py | 6 +-- pyomo/contrib/appsi/solvers/cplex.py | 10 ++-- pyomo/contrib/appsi/solvers/gurobi.py | 16 +++---- pyomo/contrib/appsi/solvers/highs.py | 6 +-- pyomo/contrib/appsi/solvers/ipopt.py | 8 ++-- pyomo/contrib/appsi/solvers/wntr.py | 6 +-- pyomo/contrib/appsi/writers/lp_writer.py | 6 +-- pyomo/contrib/appsi/writers/nl_writer.py | 6 +-- pyomo/contrib/solver/base.py | 10 ++-- pyomo/contrib/solver/gurobi.py | 16 +++---- pyomo/contrib/solver/persistent.py | 12 ++--- pyomo/contrib/solver/solution.py | 14 +++--- .../contrib/solver/tests/unit/test_results.py | 6 +-- pyomo/core/tests/unit/test_con.py | 4 +- pyomo/core/tests/unit/test_dict_objects.py | 4 +- pyomo/core/tests/unit/test_list_objects.py | 4 +- pyomo/gdp/tests/common_tests.py | 6 +-- pyomo/gdp/tests/test_bigm.py | 4 +- pyomo/gdp/tests/test_hull.py | 6 +-- .../plugins/solvers/gurobi_persistent.py | 10 ++-- 22 files changed, 105 insertions(+), 109 deletions(-) diff --git a/pyomo/contrib/appsi/base.py b/pyomo/contrib/appsi/base.py index 9d00a56e8b9..6655ec26524 100644 --- a/pyomo/contrib/appsi/base.py +++ b/pyomo/contrib/appsi/base.py @@ -21,7 +21,7 @@ Tuple, MutableMapping, ) -from pyomo.core.base.constraint import GeneralConstraintData, Constraint +from pyomo.core.base.constraint import ConstraintData, Constraint from pyomo.core.base.sos import SOSConstraintData, SOSConstraint from pyomo.core.base.var import VarData, Var from pyomo.core.base.param import ParamData, Param @@ -214,8 +214,8 @@ def get_primals( pass def get_duals( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: """ Returns a dictionary mapping constraint to dual value. @@ -233,8 +233,8 @@ def get_duals( raise NotImplementedError(f'{type(self)} does not support the get_duals method') def get_slacks( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: """ Returns a dictionary mapping constraint to slack. @@ -317,8 +317,8 @@ def get_primals( return primals def get_duals( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: if self._duals is None: raise RuntimeError( 'Solution loader does not currently have valid duals. Please ' @@ -334,8 +334,8 @@ def get_duals( return duals def get_slacks( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: if self._slacks is None: raise RuntimeError( 'Solution loader does not currently have valid slacks. Please ' @@ -727,8 +727,8 @@ def get_primals( pass def get_duals( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: """ Declare sign convention in docstring here. @@ -748,8 +748,8 @@ def get_duals( ) def get_slacks( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: """ Parameters ---------- @@ -803,7 +803,7 @@ def add_params(self, params: List[ParamData]): pass @abc.abstractmethod - def add_constraints(self, cons: List[GeneralConstraintData]): + def add_constraints(self, cons: List[ConstraintData]): pass @abc.abstractmethod @@ -819,7 +819,7 @@ def remove_params(self, params: List[ParamData]): pass @abc.abstractmethod - def remove_constraints(self, cons: List[GeneralConstraintData]): + def remove_constraints(self, cons: List[ConstraintData]): pass @abc.abstractmethod @@ -853,14 +853,14 @@ def get_primals(self, vars_to_load=None): return self._solver.get_primals(vars_to_load=vars_to_load) def get_duals( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: self._assert_solution_still_valid() return self._solver.get_duals(cons_to_load=cons_to_load) def get_slacks( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: self._assert_solution_still_valid() return self._solver.get_slacks(cons_to_load=cons_to_load) @@ -980,7 +980,7 @@ def add_params(self, params: List[ParamData]): self._add_params(params) @abc.abstractmethod - def _add_constraints(self, cons: List[GeneralConstraintData]): + def _add_constraints(self, cons: List[ConstraintData]): pass def _check_for_new_vars(self, variables: List[VarData]): @@ -1000,7 +1000,7 @@ def _check_to_remove_vars(self, variables: List[VarData]): vars_to_remove[v_id] = v self.remove_variables(list(vars_to_remove.values())) - def add_constraints(self, cons: List[GeneralConstraintData]): + def add_constraints(self, cons: List[ConstraintData]): all_fixed_vars = dict() for con in cons: if con in self._named_expressions: @@ -1128,10 +1128,10 @@ def add_block(self, block): self.set_objective(obj) @abc.abstractmethod - def _remove_constraints(self, cons: List[GeneralConstraintData]): + def _remove_constraints(self, cons: List[ConstraintData]): pass - def remove_constraints(self, cons: List[GeneralConstraintData]): + def remove_constraints(self, cons: List[ConstraintData]): self._remove_constraints(cons) for con in cons: if con not in self._named_expressions: @@ -1330,7 +1330,7 @@ def update(self, timer: HierarchicalTimer = None): for c in self._vars_referenced_by_con.keys(): if c not in current_cons_dict and c not in current_sos_dict: if (c.ctype is Constraint) or ( - c.ctype is None and isinstance(c, GeneralConstraintData) + c.ctype is None and isinstance(c, ConstraintData) ): old_cons.append(c) else: diff --git a/pyomo/contrib/appsi/fbbt.py b/pyomo/contrib/appsi/fbbt.py index 4b0d6d4876c..8e0c74b00e9 100644 --- a/pyomo/contrib/appsi/fbbt.py +++ b/pyomo/contrib/appsi/fbbt.py @@ -20,7 +20,7 @@ from typing import List, Optional from pyomo.core.base.var import VarData from pyomo.core.base.param import ParamData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.objective import ObjectiveData, minimize, maximize from pyomo.core.base.block import BlockData @@ -154,7 +154,7 @@ def _add_params(self, params: List[ParamData]): cp = cparams[ndx] cp.name = self._symbol_map.getSymbol(p, self._param_labeler) - def _add_constraints(self, cons: List[GeneralConstraintData]): + def _add_constraints(self, cons: List[ConstraintData]): cmodel.process_fbbt_constraints( self._cmodel, self._pyomo_expr_types, @@ -175,7 +175,7 @@ def _add_sos_constraints(self, cons: List[SOSConstraintData]): 'IntervalTightener does not support SOS constraints' ) - def _remove_constraints(self, cons: List[GeneralConstraintData]): + def _remove_constraints(self, cons: List[ConstraintData]): if self._symbolic_solver_labels: for c in cons: self._symbol_map.removeSymbol(c) diff --git a/pyomo/contrib/appsi/solvers/cbc.py b/pyomo/contrib/appsi/solvers/cbc.py index dffd479a5c7..08833e747e2 100644 --- a/pyomo/contrib/appsi/solvers/cbc.py +++ b/pyomo/contrib/appsi/solvers/cbc.py @@ -27,7 +27,7 @@ from pyomo.common.collections import ComponentMap from typing import Optional, Sequence, NoReturn, List, Mapping from pyomo.core.base.var import VarData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import ParamData from pyomo.core.base.objective import ObjectiveData @@ -170,7 +170,7 @@ def add_variables(self, variables: List[VarData]): def add_params(self, params: List[ParamData]): self._writer.add_params(params) - def add_constraints(self, cons: List[GeneralConstraintData]): + def add_constraints(self, cons: List[ConstraintData]): self._writer.add_constraints(cons) def add_block(self, block: BlockData): @@ -182,7 +182,7 @@ def remove_variables(self, variables: List[VarData]): def remove_params(self, params: List[ParamData]): self._writer.remove_params(params) - def remove_constraints(self, cons: List[GeneralConstraintData]): + def remove_constraints(self, cons: List[ConstraintData]): self._writer.remove_constraints(cons) def remove_block(self, block: BlockData): diff --git a/pyomo/contrib/appsi/solvers/cplex.py b/pyomo/contrib/appsi/solvers/cplex.py index 22c11bdfbe8..10de981ce7d 100644 --- a/pyomo/contrib/appsi/solvers/cplex.py +++ b/pyomo/contrib/appsi/solvers/cplex.py @@ -23,7 +23,7 @@ from pyomo.common.collections import ComponentMap from typing import Optional, Sequence, NoReturn, List, Mapping, Dict from pyomo.core.base.var import VarData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import ParamData from pyomo.core.base.objective import ObjectiveData @@ -185,7 +185,7 @@ def add_variables(self, variables: List[VarData]): def add_params(self, params: List[ParamData]): self._writer.add_params(params) - def add_constraints(self, cons: List[GeneralConstraintData]): + def add_constraints(self, cons: List[ConstraintData]): self._writer.add_constraints(cons) def add_block(self, block: BlockData): @@ -197,7 +197,7 @@ def remove_variables(self, variables: List[VarData]): def remove_params(self, params: List[ParamData]): self._writer.remove_params(params) - def remove_constraints(self, cons: List[GeneralConstraintData]): + def remove_constraints(self, cons: List[ConstraintData]): self._writer.remove_constraints(cons) def remove_block(self, block: BlockData): @@ -389,8 +389,8 @@ def get_primals( return res def get_duals( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: if ( self._cplex_model.solution.get_solution_type() == self._cplex_model.solution.type.none diff --git a/pyomo/contrib/appsi/solvers/gurobi.py b/pyomo/contrib/appsi/solvers/gurobi.py index e2ecd9b69e7..2719ecc2a00 100644 --- a/pyomo/contrib/appsi/solvers/gurobi.py +++ b/pyomo/contrib/appsi/solvers/gurobi.py @@ -24,7 +24,7 @@ from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler from pyomo.core.base.var import Var, VarData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.param import ParamData from pyomo.core.expr.numvalue import value, is_constant, is_fixed, native_numeric_types @@ -579,7 +579,7 @@ def _get_expr_from_pyomo_expr(self, expr): mutable_quadratic_coefficients, ) - def _add_constraints(self, cons: List[GeneralConstraintData]): + def _add_constraints(self, cons: List[ConstraintData]): for con in cons: conname = self._symbol_map.getSymbol(con, self._labeler) ( @@ -735,7 +735,7 @@ def _add_sos_constraints(self, cons: List[SOSConstraintData]): self._constraints_added_since_update.update(cons) self._needs_updated = True - def _remove_constraints(self, cons: List[GeneralConstraintData]): + def _remove_constraints(self, cons: List[ConstraintData]): for con in cons: if con in self._constraints_added_since_update: self._update_gurobi_model() @@ -1195,7 +1195,7 @@ def set_linear_constraint_attr(self, con, attr, val): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be modified. attr: str @@ -1272,7 +1272,7 @@ def get_linear_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -1304,7 +1304,7 @@ def get_quadratic_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -1425,7 +1425,7 @@ def cbCut(self, con): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The cut to add """ if not con.active: @@ -1510,7 +1510,7 @@ def cbLazy(self, con): """ Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The lazy constraint to add """ if not con.active: diff --git a/pyomo/contrib/appsi/solvers/highs.py b/pyomo/contrib/appsi/solvers/highs.py index c3083ac78d3..6410700c569 100644 --- a/pyomo/contrib/appsi/solvers/highs.py +++ b/pyomo/contrib/appsi/solvers/highs.py @@ -21,7 +21,7 @@ from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap from pyomo.core.base.var import VarData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.param import ParamData from pyomo.core.expr.numvalue import value, is_constant @@ -376,7 +376,7 @@ def set_instance(self, model): if self._objective is None: self.set_objective(None) - def _add_constraints(self, cons: List[GeneralConstraintData]): + def _add_constraints(self, cons: List[ConstraintData]): self._sol = None if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() @@ -462,7 +462,7 @@ def _add_sos_constraints(self, cons: List[SOSConstraintData]): 'Highs interface does not support SOS constraints' ) - def _remove_constraints(self, cons: List[GeneralConstraintData]): + def _remove_constraints(self, cons: List[ConstraintData]): self._sol = None if self._last_results_object is not None: self._last_results_object.solution_loader.invalidate() diff --git a/pyomo/contrib/appsi/solvers/ipopt.py b/pyomo/contrib/appsi/solvers/ipopt.py index 4144fbbecd9..76cd204e36d 100644 --- a/pyomo/contrib/appsi/solvers/ipopt.py +++ b/pyomo/contrib/appsi/solvers/ipopt.py @@ -29,7 +29,7 @@ from pyomo.core.expr.visitor import replace_expressions from typing import Optional, Sequence, NoReturn, List, Mapping from pyomo.core.base.var import VarData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.block import BlockData from pyomo.core.base.param import ParamData from pyomo.core.base.objective import ObjectiveData @@ -234,7 +234,7 @@ def add_variables(self, variables: List[VarData]): def add_params(self, params: List[ParamData]): self._writer.add_params(params) - def add_constraints(self, cons: List[GeneralConstraintData]): + def add_constraints(self, cons: List[ConstraintData]): self._writer.add_constraints(cons) def add_block(self, block: BlockData): @@ -246,7 +246,7 @@ def remove_variables(self, variables: List[VarData]): def remove_params(self, params: List[ParamData]): self._writer.remove_params(params) - def remove_constraints(self, cons: List[GeneralConstraintData]): + def remove_constraints(self, cons: List[ConstraintData]): self._writer.remove_constraints(cons) def remove_block(self, block: BlockData): @@ -534,7 +534,7 @@ def get_primals( res[v] = self._primal_sol[v] return res - def get_duals(self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None): + def get_duals(self, cons_to_load: Optional[Sequence[ConstraintData]] = None): if ( self._last_results_object is None or self._last_results_object.termination_condition diff --git a/pyomo/contrib/appsi/solvers/wntr.py b/pyomo/contrib/appsi/solvers/wntr.py index 62c4b0ed358..0a66cc640e5 100644 --- a/pyomo/contrib/appsi/solvers/wntr.py +++ b/pyomo/contrib/appsi/solvers/wntr.py @@ -42,7 +42,7 @@ from pyomo.core.base.block import BlockData from pyomo.core.base.var import VarData from pyomo.core.base.param import ParamData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.common.timing import HierarchicalTimer from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler from pyomo.common.dependencies import attempt_import @@ -278,7 +278,7 @@ def _add_params(self, params: List[ParamData]): setattr(self._solver_model, pname, wntr_p) self._pyomo_param_to_solver_param_map[id(p)] = wntr_p - def _add_constraints(self, cons: List[GeneralConstraintData]): + def _add_constraints(self, cons: List[ConstraintData]): aml = wntr.sim.aml.aml for con in cons: if not con.equality: @@ -294,7 +294,7 @@ def _add_constraints(self, cons: List[GeneralConstraintData]): self._pyomo_con_to_solver_con_map[con] = wntr_con self._needs_updated = True - def _remove_constraints(self, cons: List[GeneralConstraintData]): + def _remove_constraints(self, cons: List[ConstraintData]): for con in cons: solver_con = self._pyomo_con_to_solver_con_map[con] delattr(self._solver_model, solver_con.name) diff --git a/pyomo/contrib/appsi/writers/lp_writer.py b/pyomo/contrib/appsi/writers/lp_writer.py index 3a6193bd314..788dfde7892 100644 --- a/pyomo/contrib/appsi/writers/lp_writer.py +++ b/pyomo/contrib/appsi/writers/lp_writer.py @@ -12,7 +12,7 @@ from typing import List from pyomo.core.base.param import ParamData from pyomo.core.base.var import VarData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.objective import ObjectiveData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.block import BlockData @@ -99,14 +99,14 @@ def _add_params(self, params: List[ParamData]): cp.value = p.value self._pyomo_param_to_solver_param_map[id(p)] = cp - def _add_constraints(self, cons: List[GeneralConstraintData]): + def _add_constraints(self, cons: List[ConstraintData]): cmodel.process_lp_constraints(cons, self) def _add_sos_constraints(self, cons: List[SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('LP writer does not yet support SOS constraints') - def _remove_constraints(self, cons: List[GeneralConstraintData]): + def _remove_constraints(self, cons: List[ConstraintData]): for c in cons: cc = self._pyomo_con_to_solver_con_map.pop(c) self._writer.remove_constraint(cc) diff --git a/pyomo/contrib/appsi/writers/nl_writer.py b/pyomo/contrib/appsi/writers/nl_writer.py index 754bd179497..27cdca004cb 100644 --- a/pyomo/contrib/appsi/writers/nl_writer.py +++ b/pyomo/contrib/appsi/writers/nl_writer.py @@ -12,7 +12,7 @@ from typing import List from pyomo.core.base.param import ParamData from pyomo.core.base.var import VarData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.objective import ObjectiveData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.block import BlockData @@ -111,7 +111,7 @@ def _add_params(self, params: List[ParamData]): cp = cparams[ndx] cp.name = self._symbol_map.getSymbol(p, self._param_labeler) - def _add_constraints(self, cons: List[GeneralConstraintData]): + def _add_constraints(self, cons: List[ConstraintData]): cmodel.process_nl_constraints( self._writer, self._expr_types, @@ -130,7 +130,7 @@ def _add_sos_constraints(self, cons: List[SOSConstraintData]): if len(cons) != 0: raise NotImplementedError('NL writer does not support SOS constraints') - def _remove_constraints(self, cons: List[GeneralConstraintData]): + def _remove_constraints(self, cons: List[ConstraintData]): if self.config.symbolic_solver_labels: for c in cons: self._symbol_map.removeSymbol(c) diff --git a/pyomo/contrib/solver/base.py b/pyomo/contrib/solver/base.py index c53f917bc2a..45b5cca0179 100644 --- a/pyomo/contrib/solver/base.py +++ b/pyomo/contrib/solver/base.py @@ -14,7 +14,7 @@ from typing import Sequence, Dict, Optional, Mapping, NoReturn, List, Tuple import os -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.var import VarData from pyomo.core.base.param import ParamData from pyomo.core.base.block import BlockData @@ -230,8 +230,8 @@ def _get_primals( ) def _get_duals( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: """ Declare sign convention in docstring here. @@ -292,7 +292,7 @@ def add_parameters(self, params: List[ParamData]): """ @abc.abstractmethod - def add_constraints(self, cons: List[GeneralConstraintData]): + def add_constraints(self, cons: List[ConstraintData]): """ Add constraints to the model """ @@ -316,7 +316,7 @@ def remove_parameters(self, params: List[ParamData]): """ @abc.abstractmethod - def remove_constraints(self, cons: List[GeneralConstraintData]): + def remove_constraints(self, cons: List[ConstraintData]): """ Remove constraints from the model """ diff --git a/pyomo/contrib/solver/gurobi.py b/pyomo/contrib/solver/gurobi.py index ff4e93f7635..10d8120c8b3 100644 --- a/pyomo/contrib/solver/gurobi.py +++ b/pyomo/contrib/solver/gurobi.py @@ -23,7 +23,7 @@ from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base import SymbolMap, NumericLabeler, TextLabeler from pyomo.core.base.var import VarData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.sos import SOSConstraintData from pyomo.core.base.param import ParamData from pyomo.core.expr.numvalue import value, is_constant, is_fixed, native_numeric_types @@ -555,7 +555,7 @@ def _get_expr_from_pyomo_expr(self, expr): mutable_quadratic_coefficients, ) - def _add_constraints(self, cons: List[GeneralConstraintData]): + def _add_constraints(self, cons: List[ConstraintData]): for con in cons: conname = self._symbol_map.getSymbol(con, self._labeler) ( @@ -711,7 +711,7 @@ def _add_sos_constraints(self, cons: List[SOSConstraintData]): self._constraints_added_since_update.update(cons) self._needs_updated = True - def _remove_constraints(self, cons: List[GeneralConstraintData]): + def _remove_constraints(self, cons: List[ConstraintData]): for con in cons: if con in self._constraints_added_since_update: self._update_gurobi_model() @@ -1125,7 +1125,7 @@ def set_linear_constraint_attr(self, con, attr, val): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be modified. attr: str @@ -1202,7 +1202,7 @@ def get_linear_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -1234,7 +1234,7 @@ def get_quadratic_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -1355,7 +1355,7 @@ def cbCut(self, con): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The cut to add """ if not con.active: @@ -1440,7 +1440,7 @@ def cbLazy(self, con): """ Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The lazy constraint to add """ if not con.active: diff --git a/pyomo/contrib/solver/persistent.py b/pyomo/contrib/solver/persistent.py index 81d0df1334f..71322b7043e 100644 --- a/pyomo/contrib/solver/persistent.py +++ b/pyomo/contrib/solver/persistent.py @@ -12,7 +12,7 @@ import abc from typing import List -from pyomo.core.base.constraint import GeneralConstraintData, Constraint +from pyomo.core.base.constraint import ConstraintData, Constraint from pyomo.core.base.sos import SOSConstraintData, SOSConstraint from pyomo.core.base.var import VarData from pyomo.core.base.param import ParamData, Param @@ -84,7 +84,7 @@ def add_parameters(self, params: List[ParamData]): self._add_parameters(params) @abc.abstractmethod - def _add_constraints(self, cons: List[GeneralConstraintData]): + def _add_constraints(self, cons: List[ConstraintData]): pass def _check_for_new_vars(self, variables: List[VarData]): @@ -104,7 +104,7 @@ def _check_to_remove_vars(self, variables: List[VarData]): vars_to_remove[v_id] = v self.remove_variables(list(vars_to_remove.values())) - def add_constraints(self, cons: List[GeneralConstraintData]): + def add_constraints(self, cons: List[ConstraintData]): all_fixed_vars = {} for con in cons: if con in self._named_expressions: @@ -209,10 +209,10 @@ def add_block(self, block): self.set_objective(obj) @abc.abstractmethod - def _remove_constraints(self, cons: List[GeneralConstraintData]): + def _remove_constraints(self, cons: List[ConstraintData]): pass - def remove_constraints(self, cons: List[GeneralConstraintData]): + def remove_constraints(self, cons: List[ConstraintData]): self._remove_constraints(cons) for con in cons: if con not in self._named_expressions: @@ -384,7 +384,7 @@ def update(self, timer: HierarchicalTimer = None): for c in self._vars_referenced_by_con.keys(): if c not in current_cons_dict and c not in current_sos_dict: if (c.ctype is Constraint) or ( - c.ctype is None and isinstance(c, GeneralConstraintData) + c.ctype is None and isinstance(c, ConstraintData) ): old_cons.append(c) else: diff --git a/pyomo/contrib/solver/solution.py b/pyomo/contrib/solver/solution.py index e089e621f1f..a3e66475982 100644 --- a/pyomo/contrib/solver/solution.py +++ b/pyomo/contrib/solver/solution.py @@ -12,7 +12,7 @@ import abc from typing import Sequence, Dict, Optional, Mapping, NoReturn -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.var import VarData from pyomo.core.expr import value from pyomo.common.collections import ComponentMap @@ -65,8 +65,8 @@ def get_primals( """ def get_duals( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: """ Returns a dictionary mapping constraint to dual value. @@ -119,8 +119,8 @@ def get_primals(self, vars_to_load=None): return self._solver._get_primals(vars_to_load=vars_to_load) def get_duals( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: self._assert_solution_still_valid() return self._solver._get_duals(cons_to_load=cons_to_load) @@ -201,8 +201,8 @@ def get_primals( return res def get_duals( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: if self._nl_info is None: raise RuntimeError( 'Solution loader does not currently have a valid solution. Please ' diff --git a/pyomo/contrib/solver/tests/unit/test_results.py b/pyomo/contrib/solver/tests/unit/test_results.py index 6c178d80298..a15c9b87253 100644 --- a/pyomo/contrib/solver/tests/unit/test_results.py +++ b/pyomo/contrib/solver/tests/unit/test_results.py @@ -15,7 +15,7 @@ from pyomo.common import unittest from pyomo.common.config import ConfigDict -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.var import VarData from pyomo.common.collections import ComponentMap from pyomo.contrib.solver import results @@ -67,8 +67,8 @@ def get_primals( return primals def get_duals( - self, cons_to_load: Optional[Sequence[GeneralConstraintData]] = None - ) -> Dict[GeneralConstraintData, float]: + self, cons_to_load: Optional[Sequence[ConstraintData]] = None + ) -> Dict[ConstraintData, float]: if self._duals is None: raise RuntimeError( 'Solution loader does not currently have valid duals. Please ' diff --git a/pyomo/core/tests/unit/test_con.py b/pyomo/core/tests/unit/test_con.py index 26ccc7944a7..15f190e281e 100644 --- a/pyomo/core/tests/unit/test_con.py +++ b/pyomo/core/tests/unit/test_con.py @@ -44,7 +44,7 @@ InequalityExpression, RangedExpression, ) -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData class TestConstraintCreation(unittest.TestCase): @@ -1074,7 +1074,7 @@ def test_setitem(self): m.c[2] = m.x**2 <= 4 self.assertEqual(len(m.c), 1) self.assertEqual(list(m.c.keys()), [2]) - self.assertIsInstance(m.c[2], GeneralConstraintData) + self.assertIsInstance(m.c[2], ConstraintData) self.assertEqual(m.c[2].upper, 4) m.c[3] = Constraint.Skip diff --git a/pyomo/core/tests/unit/test_dict_objects.py b/pyomo/core/tests/unit/test_dict_objects.py index 16b7e0bd2e0..ef9f330bfff 100644 --- a/pyomo/core/tests/unit/test_dict_objects.py +++ b/pyomo/core/tests/unit/test_dict_objects.py @@ -18,7 +18,7 @@ ExpressionDict, ) from pyomo.core.base.var import VarData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.objective import ObjectiveData from pyomo.core.base.expression import ExpressionData @@ -375,7 +375,7 @@ def setUp(self): class TestConstraintDict(_TestActiveComponentDictBase, unittest.TestCase): _ctype = ConstraintDict - _cdatatype = GeneralConstraintData + _cdatatype = ConstraintData def setUp(self): _TestComponentDictBase.setUp(self) diff --git a/pyomo/core/tests/unit/test_list_objects.py b/pyomo/core/tests/unit/test_list_objects.py index 94913bcbc02..671a8429e06 100644 --- a/pyomo/core/tests/unit/test_list_objects.py +++ b/pyomo/core/tests/unit/test_list_objects.py @@ -18,7 +18,7 @@ XExpressionList, ) from pyomo.core.base.var import VarData -from pyomo.core.base.constraint import GeneralConstraintData +from pyomo.core.base.constraint import ConstraintData from pyomo.core.base.objective import ObjectiveData from pyomo.core.base.expression import ExpressionData @@ -392,7 +392,7 @@ def setUp(self): class TestConstraintList(_TestActiveComponentListBase, unittest.TestCase): _ctype = XConstraintList - _cdatatype = GeneralConstraintData + _cdatatype = ConstraintData def setUp(self): _TestComponentListBase.setUp(self) diff --git a/pyomo/gdp/tests/common_tests.py b/pyomo/gdp/tests/common_tests.py index 233c3ca9c09..50bc8b05f86 100644 --- a/pyomo/gdp/tests/common_tests.py +++ b/pyomo/gdp/tests/common_tests.py @@ -952,9 +952,7 @@ def check_disjunction_data_target(self, transformation): transBlock = m.component("_pyomo_gdp_%s_reformulation" % transformation) self.assertIsInstance(transBlock, Block) self.assertIsInstance(transBlock.component("disjunction_xor"), Constraint) - self.assertIsInstance( - transBlock.disjunction_xor[2], constraint.GeneralConstraintData - ) + self.assertIsInstance(transBlock.disjunction_xor[2], constraint.ConstraintData) self.assertIsInstance(transBlock.component("relaxedDisjuncts"), Block) self.assertEqual(len(transBlock.relaxedDisjuncts), 3) @@ -963,7 +961,7 @@ def check_disjunction_data_target(self, transformation): m, targets=[m.disjunction[1]] ) self.assertIsInstance( - m.disjunction[1].algebraic_constraint, constraint.GeneralConstraintData + m.disjunction[1].algebraic_constraint, constraint.ConstraintData ) transBlock = m.component("_pyomo_gdp_%s_reformulation_4" % transformation) self.assertIsInstance(transBlock, Block) diff --git a/pyomo/gdp/tests/test_bigm.py b/pyomo/gdp/tests/test_bigm.py index efef4c5fb1f..cf42eb260ff 100644 --- a/pyomo/gdp/tests/test_bigm.py +++ b/pyomo/gdp/tests/test_bigm.py @@ -1323,8 +1323,8 @@ def test_do_not_transform_deactivated_constraintDatas(self): self.assertEqual(len(cons_list), 2) lb = cons_list[0] ub = cons_list[1] - self.assertIsInstance(lb, constraint.GeneralConstraintData) - self.assertIsInstance(ub, constraint.GeneralConstraintData) + self.assertIsInstance(lb, constraint.ConstraintData) + self.assertIsInstance(ub, constraint.ConstraintData) def checkMs( self, m, disj1c1lb, disj1c1ub, disj1c2lb, disj1c2ub, disj2c1ub, disj2c2ub diff --git a/pyomo/gdp/tests/test_hull.py b/pyomo/gdp/tests/test_hull.py index 6093e01dc25..07876a9d213 100644 --- a/pyomo/gdp/tests/test_hull.py +++ b/pyomo/gdp/tests/test_hull.py @@ -1252,12 +1252,10 @@ def check_second_iteration(self, model): orig = model.component("_pyomo_gdp_hull_reformulation") self.assertIsInstance( - model.disjunctionList[1].algebraic_constraint, - constraint.GeneralConstraintData, + model.disjunctionList[1].algebraic_constraint, constraint.ConstraintData ) self.assertIsInstance( - model.disjunctionList[0].algebraic_constraint, - constraint.GeneralConstraintData, + model.disjunctionList[0].algebraic_constraint, constraint.ConstraintData ) self.assertFalse(model.disjunctionList[1].active) self.assertFalse(model.disjunctionList[0].active) diff --git a/pyomo/solvers/plugins/solvers/gurobi_persistent.py b/pyomo/solvers/plugins/solvers/gurobi_persistent.py index 17ce33fd95f..94a2ac6b734 100644 --- a/pyomo/solvers/plugins/solvers/gurobi_persistent.py +++ b/pyomo/solvers/plugins/solvers/gurobi_persistent.py @@ -157,7 +157,7 @@ def set_linear_constraint_attr(self, con, attr, val): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be modified. attr: str @@ -384,7 +384,7 @@ def get_linear_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -431,7 +431,7 @@ def get_quadratic_constraint_attr(self, con, attr): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The pyomo constraint for which the corresponding gurobi constraint attribute should be retrieved. attr: str @@ -569,7 +569,7 @@ def cbCut(self, con): Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The cut to add """ if not con.active: @@ -647,7 +647,7 @@ def cbLazy(self, con): """ Parameters ---------- - con: pyomo.core.base.constraint.GeneralConstraintData + con: pyomo.core.base.constraint.ConstraintData The lazy constraint to add """ if not con.active: From ef522d9338eb8722737d0522fe65bfd8e3c96ec9 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 21 Mar 2024 15:25:22 -0600 Subject: [PATCH 48/83] Fix base class --- pyomo/core/base/constraint.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyomo/core/base/constraint.py b/pyomo/core/base/constraint.py index 08c97d7c8ae..3a71758d55d 100644 --- a/pyomo/core/base/constraint.py +++ b/pyomo/core/base/constraint.py @@ -125,7 +125,7 @@ def C_rule(model, i, j): return rule_wrapper(rule, result_map, map_types=map_types) -class ConstraintData(ConstraintData): +class ConstraintData(ActiveComponentData): """ This class defines the data for a single general constraint. From a573244f008af69eceb39c0812cd3d30b09df268 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Sat, 23 Mar 2024 06:32:30 -0600 Subject: [PATCH 49/83] Rename _ComponentBase -> ComponentBase --- pyomo/core/base/component.py | 12 +++++++++--- pyomo/core/base/set.py | 4 ++-- pyomo/core/util.py | 6 +++--- pyomo/gdp/util.py | 1 - 4 files changed, 14 insertions(+), 9 deletions(-) diff --git a/pyomo/core/base/component.py b/pyomo/core/base/component.py index 50cf264c799..7dea5b7dde5 100644 --- a/pyomo/core/base/component.py +++ b/pyomo/core/base/component.py @@ -20,6 +20,7 @@ from pyomo.common.autoslots import AutoSlots, fast_deepcopy from pyomo.common.collections import OrderedDict from pyomo.common.deprecation import ( + RenamedClass, deprecated, deprecation_warning, relocated_module_attribute, @@ -79,7 +80,7 @@ class CloneError(pyomo.common.errors.PyomoException): pass -class _ComponentBase(PyomoObject): +class ComponentBase(PyomoObject): """A base class for Component and ComponentData This class defines some fundamental methods and properties that are @@ -474,7 +475,12 @@ def _pprint_base_impl( ostream.write(_data) -class Component(_ComponentBase): +class _ComponentBase(metaclass=RenamedClass): + __renamed__new_class__ = ComponentBase + __renamed__version__ = '6.7.2.dev0' + + +class Component(ComponentBase): """ This is the base class for all Pyomo modeling components. @@ -779,7 +785,7 @@ def deactivate(self): self._active = False -class ComponentData(_ComponentBase): +class ComponentData(ComponentBase): """ This is the base class for the component data used in Pyomo modeling components. Subclasses of ComponentData are diff --git a/pyomo/core/base/set.py b/pyomo/core/base/set.py index d94cc86cf7c..fbf1ac60900 100644 --- a/pyomo/core/base/set.py +++ b/pyomo/core/base/set.py @@ -50,7 +50,7 @@ RangeDifferenceError, ) from pyomo.core.base.component import ( - _ComponentBase, + ComponentBase, Component, ComponentData, ModelComponentFactory, @@ -140,7 +140,7 @@ def process_setarg(arg): _anonymous.update(arg._anonymous_sets) return arg, _anonymous - elif isinstance(arg, _ComponentBase): + elif isinstance(arg, ComponentBase): if isinstance(arg, IndexedComponent) and arg.is_indexed(): raise TypeError( "Cannot apply a Set operator to an " diff --git a/pyomo/core/util.py b/pyomo/core/util.py index f337b487cef..4b6cc8f3320 100644 --- a/pyomo/core/util.py +++ b/pyomo/core/util.py @@ -18,7 +18,7 @@ from pyomo.core.expr.numeric_expr import mutable_expression, NPV_SumExpression from pyomo.core.base.var import Var from pyomo.core.base.expression import Expression -from pyomo.core.base.component import _ComponentBase +from pyomo.core.base.component import ComponentBase import logging logger = logging.getLogger(__name__) @@ -238,12 +238,12 @@ def sequence(*args): def target_list(x): - if isinstance(x, _ComponentBase): + if isinstance(x, ComponentBase): return [x] elif hasattr(x, '__iter__'): ans = [] for i in x: - if isinstance(i, _ComponentBase): + if isinstance(i, ComponentBase): ans.append(i) else: raise ValueError( diff --git a/pyomo/gdp/util.py b/pyomo/gdp/util.py index 686253b0179..932a2ddf451 100644 --- a/pyomo/gdp/util.py +++ b/pyomo/gdp/util.py @@ -13,7 +13,6 @@ from pyomo.gdp.disjunct import DisjunctData, Disjunct import pyomo.core.expr as EXPR -from pyomo.core.base.component import _ComponentBase from pyomo.core import ( Block, Suffix, From b75a974378012d4319668961f99a91668aab6446 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Sat, 23 Mar 2024 06:46:04 -0600 Subject: [PATCH 50/83] Remove _SetDataBase --- pyomo/core/base/reference.py | 6 +++--- pyomo/core/base/set.py | 26 ++++++++++---------------- 2 files changed, 13 insertions(+), 19 deletions(-) diff --git a/pyomo/core/base/reference.py b/pyomo/core/base/reference.py index 2279db067a6..fd6ba192c70 100644 --- a/pyomo/core/base/reference.py +++ b/pyomo/core/base/reference.py @@ -18,7 +18,7 @@ Sequence, ) from pyomo.common.modeling import NOTSET -from pyomo.core.base.set import DeclareGlobalSet, Set, SetOf, OrderedSetOf, _SetDataBase +from pyomo.core.base.set import DeclareGlobalSet, Set, SetOf, OrderedSetOf, SetData from pyomo.core.base.component import Component, ComponentData from pyomo.core.base.global_set import UnindexedComponent_set from pyomo.core.base.enums import SortComponents @@ -774,10 +774,10 @@ def Reference(reference, ctype=NOTSET): # is that within the subsets list, and set is a wildcard set. index = wildcards[0][1] # index is the first wildcard set. - if not isinstance(index, _SetDataBase): + if not isinstance(index, SetData): index = SetOf(index) for lvl, idx in wildcards[1:]: - if not isinstance(idx, _SetDataBase): + if not isinstance(idx, SetData): idx = SetOf(idx) index = index * idx # index is now either a single Set, or a SetProduct of the diff --git a/pyomo/core/base/set.py b/pyomo/core/base/set.py index fbf1ac60900..b9a2fe72e1d 100644 --- a/pyomo/core/base/set.py +++ b/pyomo/core/base/set.py @@ -84,10 +84,7 @@ All Sets implement one of the following APIs: -0. `class _SetDataBase(ComponentData)` - *(pure virtual interface)* - -1. `class SetData(_SetDataBase)` +1. `class SetData(ComponentData)` *(base class for all AML Sets)* 2. `class _FiniteSetMixin(object)` @@ -128,7 +125,7 @@ def process_setarg(arg): - if isinstance(arg, _SetDataBase): + if isinstance(arg, SetData): if ( getattr(arg, '_parent', None) is not None or getattr(arg, '_anonymous_sets', None) is GlobalSetBase @@ -512,16 +509,8 @@ class _NotFound(object): pass -# A trivial class that we can use to test if an object is a "legitimate" -# set (either ScalarSet, or a member of an IndexedSet) -class _SetDataBase(ComponentData): - """The base for all objects that can be used as a component indexing set.""" - - __slots__ = () - - -class SetData(_SetDataBase): - """The base for all Pyomo AML objects that can be used as a component +class SetData(ComponentData): + """The base for all Pyomo objects that can be used as a component indexing set. Derived versions of this class can be used as the Index for any @@ -1193,6 +1182,11 @@ class _SetData(metaclass=RenamedClass): __renamed__version__ = '6.7.2.dev0' +class _SetDataBase(metaclass=RenamedClass): + __renamed__new_class__ = SetData + __renamed__version__ = '6.7.2.dev0' + + class _FiniteSetMixin(object): __slots__ = () @@ -3496,7 +3490,7 @@ def _domain(self, val): def _checkArgs(*sets): ans = [] for s in sets: - if isinstance(s, _SetDataBase): + if isinstance(s, SetData): ans.append((s.isordered(), s.isfinite())) elif type(s) in {tuple, list}: ans.append((True, True)) From 4d8e1c3d7c6229dcfe712d7f71e125bc74f127cc Mon Sep 17 00:00:00 2001 From: John Siirola Date: Sun, 31 Mar 2024 13:23:48 -0600 Subject: [PATCH 51/83] Move from isinstance to ctype for verifying component type --- .../piecewise_to_gdp_transformation.py | 4 +-- .../core/plugins/transform/add_slack_vars.py | 5 ++-- pyomo/core/plugins/transform/scaling.py | 6 ++--- pyomo/repn/plugins/nl_writer.py | 25 +++++++++++-------- pyomo/util/calc_var_value.py | 4 +-- pyomo/util/report_scaling.py | 4 +-- 6 files changed, 24 insertions(+), 24 deletions(-) diff --git a/pyomo/contrib/piecewise/transform/piecewise_to_gdp_transformation.py b/pyomo/contrib/piecewise/transform/piecewise_to_gdp_transformation.py index 779bb601c71..5417cbc17f4 100644 --- a/pyomo/contrib/piecewise/transform/piecewise_to_gdp_transformation.py +++ b/pyomo/contrib/piecewise/transform/piecewise_to_gdp_transformation.py @@ -33,7 +33,7 @@ Any, ) from pyomo.core.base import Transformation -from pyomo.core.base.block import BlockData, Block +from pyomo.core.base.block import Block from pyomo.core.util import target_list from pyomo.gdp import Disjunct, Disjunction from pyomo.gdp.util import is_child_of @@ -147,7 +147,7 @@ def _apply_to_impl(self, instance, **kwds): self._transform_piecewise_linear_function( t, config.descend_into_expressions ) - elif t.ctype is Block or isinstance(t, BlockData): + elif issubclass(t.ctype, Block): self._transform_block(t, config.descend_into_expressions) elif t.ctype is Constraint: if not config.descend_into_expressions: diff --git a/pyomo/core/plugins/transform/add_slack_vars.py b/pyomo/core/plugins/transform/add_slack_vars.py index 0007f8de7ad..39903384729 100644 --- a/pyomo/core/plugins/transform/add_slack_vars.py +++ b/pyomo/core/plugins/transform/add_slack_vars.py @@ -23,7 +23,6 @@ from pyomo.core.plugins.transform.hierarchy import NonIsomorphicTransformation from pyomo.common.config import ConfigBlock, ConfigValue from pyomo.core.base import ComponentUID -from pyomo.core.base.constraint import ConstraintData from pyomo.common.deprecation import deprecation_warning @@ -42,7 +41,7 @@ def target_list(x): # [ESJ 07/15/2020] We have to just pass it through because we need the # instance in order to be able to do anything about it... return [x] - elif isinstance(x, (Constraint, ConstraintData)): + elif getattr(x, 'ctype', None) is Constraint: return [x] elif hasattr(x, '__iter__'): ans = [] @@ -53,7 +52,7 @@ def target_list(x): deprecation_msg = None # same as above... ans.append(i) - elif isinstance(i, (Constraint, ConstraintData)): + elif getattr(i, 'ctype', None) is Constraint: ans.append(i) else: raise ValueError( diff --git a/pyomo/core/plugins/transform/scaling.py b/pyomo/core/plugins/transform/scaling.py index ef418f094ae..e962352668c 100644 --- a/pyomo/core/plugins/transform/scaling.py +++ b/pyomo/core/plugins/transform/scaling.py @@ -15,8 +15,6 @@ Var, Constraint, Objective, - ConstraintData, - ObjectiveData, Suffix, value, ) @@ -197,7 +195,7 @@ def _apply_to(self, model, rename=True): already_scaled.add(id(c)) # perform the constraint/objective scaling and variable sub scaling_factor = component_scaling_factor_map[c] - if isinstance(c, ConstraintData): + if c.ctype is Constraint: body = scaling_factor * replace_expressions( expr=c.body, substitution_map=variable_substitution_dict, @@ -226,7 +224,7 @@ def _apply_to(self, model, rename=True): else: c.set_value((lower, body, upper)) - elif isinstance(c, ObjectiveData): + elif c.ctype is Objective: c.expr = scaling_factor * replace_expressions( expr=c.expr, substitution_map=variable_substitution_dict, diff --git a/pyomo/repn/plugins/nl_writer.py b/pyomo/repn/plugins/nl_writer.py index 8cc73b5e3fe..76599f74228 100644 --- a/pyomo/repn/plugins/nl_writer.py +++ b/pyomo/repn/plugins/nl_writer.py @@ -437,6 +437,7 @@ def store(self, obj, val): self.values[obj] = val def compile(self, column_order, row_order, obj_order, model_id): + var_con_obj = {Var, Constraint, Objective} missing_component_data = ComponentSet() unknown_data = ComponentSet() queue = [self.values.items()] @@ -462,18 +463,20 @@ def compile(self, column_order, row_order, obj_order, model_id): self.obj[obj_order[_id]] = val elif _id == model_id: self.prob[0] = val - elif isinstance(obj, (VarData, ConstraintData, ObjectiveData)): - missing_component_data.add(obj) - elif isinstance(obj, (Var, Constraint, Objective)): - # Expand this indexed component to store the - # individual ComponentDatas, but ONLY if the - # component data is not in the original dictionary - # of values that we extracted from the Suffixes - queue.append( - product( - filterfalse(self.values.__contains__, obj.values()), (val,) + elif getattr(obj, 'ctype', None) in var_con_obj: + if obj.is_indexed(): + # Expand this indexed component to store the + # individual ComponentDatas, but ONLY if the + # component data is not in the original dictionary + # of values that we extracted from the Suffixes + queue.append( + product( + filterfalse(self.values.__contains__, obj.values()), + (val,), + ) ) - ) + else: + missing_component_data.add(obj) else: unknown_data.add(obj) if missing_component_data: diff --git a/pyomo/util/calc_var_value.py b/pyomo/util/calc_var_value.py index 254b82c59cd..156ad56dffb 100644 --- a/pyomo/util/calc_var_value.py +++ b/pyomo/util/calc_var_value.py @@ -12,7 +12,7 @@ from pyomo.common.errors import IterationLimitError from pyomo.common.numeric_types import native_numeric_types, native_complex_types, value from pyomo.core.expr.calculus.derivatives import differentiate -from pyomo.core.base.constraint import Constraint, ConstraintData +from pyomo.core.base.constraint import Constraint import logging @@ -81,7 +81,7 @@ def calculate_variable_from_constraint( """ # Leverage all the Constraint logic to process the incoming tuple/expression - if not isinstance(constraint, ConstraintData): + if not getattr(constraint, 'ctype', None) is Constraint: constraint = Constraint(expr=constraint, name=type(constraint).__name__) constraint.construct() diff --git a/pyomo/util/report_scaling.py b/pyomo/util/report_scaling.py index 7619662c482..02b3710c334 100644 --- a/pyomo/util/report_scaling.py +++ b/pyomo/util/report_scaling.py @@ -13,7 +13,7 @@ import math from pyomo.core.base.block import BlockData from pyomo.common.collections import ComponentSet -from pyomo.core.base.var import VarData +from pyomo.core.base.var import Var from pyomo.contrib.fbbt.fbbt import compute_bounds_on_expr from pyomo.core.expr.calculus.diff_with_pyomo import reverse_sd import logging @@ -73,7 +73,7 @@ def _check_coefficients( ): ders = reverse_sd(expr) for _v, _der in ders.items(): - if isinstance(_v, VarData): + if getattr(_v, 'ctype', None) is Var: if _v.is_fixed(): continue der_lb, der_ub = compute_bounds_on_expr(_der) From 9d4b9131c76b337a41ff12cf4ea6f55062ae3115 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Sun, 31 Mar 2024 19:41:34 -0600 Subject: [PATCH 52/83] NFC: apply black --- pyomo/core/plugins/transform/scaling.py | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-) diff --git a/pyomo/core/plugins/transform/scaling.py b/pyomo/core/plugins/transform/scaling.py index e962352668c..11d4ac8c493 100644 --- a/pyomo/core/plugins/transform/scaling.py +++ b/pyomo/core/plugins/transform/scaling.py @@ -10,14 +10,7 @@ # ___________________________________________________________________________ from pyomo.common.collections import ComponentMap -from pyomo.core.base import ( - Block, - Var, - Constraint, - Objective, - Suffix, - value, -) +from pyomo.core.base import Block, Var, Constraint, Objective, Suffix, value from pyomo.core.plugins.transform.hierarchy import Transformation from pyomo.core.base import TransformationFactory from pyomo.core.base.suffix import SuffixFinder From f2fd07c893fe5d13a6926407324fe4594a799f75 Mon Sep 17 00:00:00 2001 From: Miranda Mundt Date: Tue, 2 Apr 2024 13:49:44 -0600 Subject: [PATCH 53/83] Skip Tests on Draft and WIP Pull Requests --- .github/workflows/test_pr_and_main.yml | 9 ++++++++- doc/OnlineDocs/contribution_guide.rst | 13 ++++++++++--- 2 files changed, 18 insertions(+), 4 deletions(-) diff --git a/.github/workflows/test_pr_and_main.yml b/.github/workflows/test_pr_and_main.yml index 76ec6de951a..72366eb1353 100644 --- a/.github/workflows/test_pr_and_main.yml +++ b/.github/workflows/test_pr_and_main.yml @@ -7,6 +7,11 @@ on: pull_request: branches: - main + types: + - opened + - reopened + - synchronize + - ready_for_review workflow_dispatch: inputs: git-ref: @@ -34,6 +39,8 @@ jobs: lint: name: lint/style-and-typos runs-on: ubuntu-latest + if: | + contains(github.event.pull_request.title, '[WIP]') != true && !github.event.pull_request.draft steps: - name: Checkout Pyomo source uses: actions/checkout@v4 @@ -733,7 +740,7 @@ jobs: cover: name: process-coverage-${{ matrix.TARGET }} needs: build - if: always() # run even if a build job fails + if: success() || failure() # run even if a build job fails, but not if cancelled runs-on: ${{ matrix.os }} timeout-minutes: 10 strategy: diff --git a/doc/OnlineDocs/contribution_guide.rst b/doc/OnlineDocs/contribution_guide.rst index 10670627546..285bb656406 100644 --- a/doc/OnlineDocs/contribution_guide.rst +++ b/doc/OnlineDocs/contribution_guide.rst @@ -71,6 +71,10 @@ at least 70% coverage of the lines modified in the PR and prefer coverage closer to 90%. We also require that all tests pass before a PR will be merged. +.. note:: + If you are having issues getting tests to pass on your Pull Request, + please tag any of the core developers to ask for help. + The Pyomo main branch provides a Github Actions workflow (configured in the ``.github/`` directory) that will test any changes pushed to a branch with a subset of the complete test harness that includes @@ -82,13 +86,16 @@ This will enable the tests to run automatically with each push to your fork. At any point in the development cycle, a "work in progress" pull request may be opened by including '[WIP]' at the beginning of the PR -title. This allows your code changes to be tested by the full suite of -Pyomo's automatic -testing infrastructure. Any pull requests marked '[WIP]' will not be +title. Any pull requests marked '[WIP]' or draft will not be reviewed or merged by the core development team. However, any '[WIP]' pull request left open for an extended period of time without active development may be marked 'stale' and closed. +.. note:: + Draft and WIP Pull Requests will **NOT** trigger tests. This is an effort to + keep our backlog as available as possible. Please liberally use the provided + branch testing for draft functionality. + Python Version Support ++++++++++++++++++++++ From b082419502a7c024990c28a54d91bb3069bea011 Mon Sep 17 00:00:00 2001 From: Miranda Mundt Date: Tue, 2 Apr 2024 13:57:37 -0600 Subject: [PATCH 54/83] Change language for branch test request --- doc/OnlineDocs/contribution_guide.rst | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/doc/OnlineDocs/contribution_guide.rst b/doc/OnlineDocs/contribution_guide.rst index 285bb656406..6054a8d2ba9 100644 --- a/doc/OnlineDocs/contribution_guide.rst +++ b/doc/OnlineDocs/contribution_guide.rst @@ -93,8 +93,8 @@ active development may be marked 'stale' and closed. .. note:: Draft and WIP Pull Requests will **NOT** trigger tests. This is an effort to - keep our backlog as available as possible. Please liberally use the provided - branch testing for draft functionality. + keep our backlog as available as possible. Please make use of the provided + branch test suite for evaluating / testing draft functionality. Python Version Support ++++++++++++++++++++++ From 009f0d9af07c726977fa401502bc26fca52249c7 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Tue, 2 Apr 2024 15:37:44 -0600 Subject: [PATCH 55/83] Replace ProblemSense and the constants in kernel.objective with ObjectiveSense enum --- pyomo/common/enums.py | 38 ++++++++++++++++++++++++++++++++++ pyomo/core/kernel/objective.py | 5 +---- pyomo/opt/results/problem.py | 38 +++++++++++++++++++++++----------- 3 files changed, 65 insertions(+), 16 deletions(-) create mode 100644 pyomo/common/enums.py diff --git a/pyomo/common/enums.py b/pyomo/common/enums.py new file mode 100644 index 00000000000..c685843b41c --- /dev/null +++ b/pyomo/common/enums.py @@ -0,0 +1,38 @@ +# ___________________________________________________________________________ +# +# Pyomo: Python Optimization Modeling Objects +# Copyright (c) 2008-2024 +# National Technology and Engineering Solutions of Sandia, LLC +# Under the terms of Contract DE-NA0003525 with National Technology and +# Engineering Solutions of Sandia, LLC, the U.S. Government retains certain +# rights in this software. +# This software is distributed under the 3-clause BSD License. +# ___________________________________________________________________________ + +import enum + +from pyomo.common.deprecation import RenamedClass + +class ObjectiveSense(enum.IntEnum): + """Flag indicating if an objective is minimizing (1) or maximizing (-1). + + While the numeric values are arbitrary, there are parts of Pyomo + that rely on this particular choice of value. These values are also + consistent with some solvers (notably Gurobi). + + """ + minimize = 1 + maximize = -1 + + # Overloading __str__ is needed to match the behavior of the old + # pyutilib.enum class (removed June 2020). There are spots in the + # code base that expect the string representation for items in the + # enum to not include the class name. New uses of enum shouldn't + # need to do this. + def __str__(self): + return self.name + +minimize = ObjectiveSense.minimize +maximize = ObjectiveSense.maximize + + diff --git a/pyomo/core/kernel/objective.py b/pyomo/core/kernel/objective.py index 9aa8e3315ef..840c7cfd7e0 100644 --- a/pyomo/core/kernel/objective.py +++ b/pyomo/core/kernel/objective.py @@ -9,15 +9,12 @@ # This software is distributed under the 3-clause BSD License. # ___________________________________________________________________________ +from pyomo.common.enums import minimize, maximize from pyomo.core.expr.numvalue import as_numeric from pyomo.core.kernel.base import _abstract_readwrite_property from pyomo.core.kernel.container_utils import define_simple_containers from pyomo.core.kernel.expression import IExpression -# Constants used to define the optimization sense -minimize = 1 -maximize = -1 - class IObjective(IExpression): """ diff --git a/pyomo/opt/results/problem.py b/pyomo/opt/results/problem.py index 98f749f3aeb..e35bb155355 100644 --- a/pyomo/opt/results/problem.py +++ b/pyomo/opt/results/problem.py @@ -12,19 +12,33 @@ import enum from pyomo.opt.results.container import MapContainer +from pyomo.common.deprecation import deprecated, deprecation_warning +from pyomo.common.enums import ObjectiveSense -class ProblemSense(str, enum.Enum): - unknown = 'unknown' - minimize = 'minimize' - maximize = 'maximize' - # Overloading __str__ is needed to match the behavior of the old - # pyutilib.enum class (removed June 2020). There are spots in the - # code base that expect the string representation for items in the - # enum to not include the class name. New uses of enum shouldn't - # need to do this. - def __str__(self): - return self.value +class ProblemSenseType(type): + @deprecated( + "pyomo.opt.results.problem.ProblemSense has been replaced by " + "pyomo.common.enums.ObjectiveSense", + version="6.7.2.dev0", + ) + def __getattr__(cls, attr): + if attr == 'minimize': + return ObjectiveSense.minimize + if attr == 'maximize': + return ObjectiveSense.maximize + if attr == 'unknown': + deprecation_warning( + "ProblemSense.unknown is no longer an allowable option. " + "Mapping 'unknown' to 'minimize'", + version="6.7.2.dev0", + ) + return ObjectiveSense.minimize + raise AttributeError(attr) + + +class ProblemSense(metaclass=ProblemSenseType): + pass class ProblemInformation(MapContainer): @@ -40,4 +54,4 @@ def __init__(self): self.declare('number_of_integer_variables') self.declare('number_of_continuous_variables') self.declare('number_of_nonzeros') - self.declare('sense', value=ProblemSense.unknown, required=True) + self.declare('sense', value=ProblemSense.minimize, required=True) From ea7c23704b7b97e08029e283891e8213f9e771bb Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 11:12:23 -0600 Subject: [PATCH 56/83] Make ProblemSense an extension of the ObjectiveSense enum --- pyomo/common/enums.py | 102 +++++++++++++++++++++++++++++++++-- pyomo/opt/results/problem.py | 38 ++++--------- 2 files changed, 110 insertions(+), 30 deletions(-) diff --git a/pyomo/common/enums.py b/pyomo/common/enums.py index c685843b41c..7f00e87a85f 100644 --- a/pyomo/common/enums.py +++ b/pyomo/common/enums.py @@ -10,8 +10,97 @@ # ___________________________________________________________________________ import enum +import itertools + + +class ExtendedEnumType(enum.EnumType): + """Metaclass for creating an :py:class:`Enum` that extends another Enum + + In general, :py:class:`Enum` classes are not extensible: that is, + they are frozen when defined and cannot be the base class of another + Enum. This Metaclass provides a workaround for creating a new Enum + that extends an existing enum. Members in the base Enum are all + present as members on the extended enum. + + Example + ------- + + .. testcode:: + :hide: + + import enum + from pyomo.common.enums import ExtendedEnumType + + .. testcode:: + + class ObjectiveSense(enum.IntEnum): + minimize = 1 + maximize = -1 + + class ProblemSense(enum.IntEnum, metaclass=ExtendedEnumType): + __base_enum__ = ObjectiveSense + + unknown = 0 + + .. doctest:: + + >>> list(ProblemSense) + [, , ] + >>> ProblemSense.unknown + + >>> ProblemSense.maximize + + >>> ProblemSense(0) + + >>> ProblemSense(1) + + >>> ProblemSense('unknown') + + >>> ProblemSense('maximize') + + >>> hasattr(ProblemSense, 'minimize') + True + >>> hasattr(ProblemSense, 'unknown') + True + >>> ProblemSense.minimize is ObjectiveSense.minimize + True + + """ + + def __getattr__(cls, attr): + try: + return getattr(cls.__base_enum__, attr) + except: + return super().__getattr__(attr) + + def __iter__(cls): + # The members of this Enum are the base enum members joined with + # the local members + return itertools.chain(super().__iter__(), cls.__base_enum__.__iter__()) + + def __instancecheck__(cls, instance): + if cls.__subclasscheck__(type(instance)): + return True + # Also pretend that members of the extended enum are subclasses + # of the __base_enum__. This is needed to circumvent error + # checking in enum.__new__ (e.g., for `ProblemSense('minimize')`) + return cls.__base_enum__.__subclasscheck__(type(instance)) + + def _missing_(cls, value): + # Support attribute lookup by value or name + for attr in ('value', 'name'): + for member in cls: + if getattr(member, attr) == value: + return member + return None + + def __new__(metacls, cls, bases, classdict, **kwds): + # Support lookup by name - but only if the new Enum doesn't + # specify it's own implementation of _missing_ + if '_missing_' not in classdict: + classdict['_missing_'] = classmethod(ExtendedEnumType._missing_) + return super().__new__(metacls, cls, bases, classdict, **kwds) -from pyomo.common.deprecation import RenamedClass class ObjectiveSense(enum.IntEnum): """Flag indicating if an objective is minimizing (1) or maximizing (-1). @@ -21,6 +110,7 @@ class ObjectiveSense(enum.IntEnum): consistent with some solvers (notably Gurobi). """ + minimize = 1 maximize = -1 @@ -32,7 +122,13 @@ class ObjectiveSense(enum.IntEnum): def __str__(self): return self.name -minimize = ObjectiveSense.minimize -maximize = ObjectiveSense.maximize + @classmethod + def _missing_(cls, value): + for member in cls: + if member.name == value: + return member + return None +minimize = ObjectiveSense.minimize +maximize = ObjectiveSense.maximize diff --git a/pyomo/opt/results/problem.py b/pyomo/opt/results/problem.py index e35bb155355..34da8f91918 100644 --- a/pyomo/opt/results/problem.py +++ b/pyomo/opt/results/problem.py @@ -13,32 +13,16 @@ from pyomo.opt.results.container import MapContainer from pyomo.common.deprecation import deprecated, deprecation_warning -from pyomo.common.enums import ObjectiveSense - - -class ProblemSenseType(type): - @deprecated( - "pyomo.opt.results.problem.ProblemSense has been replaced by " - "pyomo.common.enums.ObjectiveSense", - version="6.7.2.dev0", - ) - def __getattr__(cls, attr): - if attr == 'minimize': - return ObjectiveSense.minimize - if attr == 'maximize': - return ObjectiveSense.maximize - if attr == 'unknown': - deprecation_warning( - "ProblemSense.unknown is no longer an allowable option. " - "Mapping 'unknown' to 'minimize'", - version="6.7.2.dev0", - ) - return ObjectiveSense.minimize - raise AttributeError(attr) - - -class ProblemSense(metaclass=ProblemSenseType): - pass +from pyomo.common.enums import ExtendedEnumType, ObjectiveSense + + +class ProblemSense(enum.IntEnum, metaclass=ExtendedEnumType): + __base_enum__ = ObjectiveSense + + unknown = 0 + + def __str__(self): + return self.name class ProblemInformation(MapContainer): @@ -54,4 +38,4 @@ def __init__(self): self.declare('number_of_integer_variables') self.declare('number_of_continuous_variables') self.declare('number_of_nonzeros') - self.declare('sense', value=ProblemSense.minimize, required=True) + self.declare('sense', value=ProblemSense.unknown, required=True) From 297ce1d1f5f0a2d64c61a121ae35d63fd3f1509e Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 11:27:57 -0600 Subject: [PATCH 57/83] Switch Objective.sense to store ObjectiveSense enum values --- pyomo/core/__init__.py | 2 +- pyomo/core/base/__init__.py | 2 +- pyomo/core/base/objective.py | 26 ++++---------------------- pyomo/core/kernel/objective.py | 11 ++--------- 4 files changed, 8 insertions(+), 33 deletions(-) diff --git a/pyomo/core/__init__.py b/pyomo/core/__init__.py index bce79faacc5..f0d168d98f9 100644 --- a/pyomo/core/__init__.py +++ b/pyomo/core/__init__.py @@ -101,7 +101,7 @@ BooleanValue, native_logical_values, ) -from pyomo.core.kernel.objective import minimize, maximize +from pyomo.core.base import minimize, maximize from pyomo.core.base.config import PyomoOptions from pyomo.core.base.expression import Expression diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 4bbd0c9dc44..df5ce743888 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -12,6 +12,7 @@ # TODO: this import is for historical backwards compatibility and should # probably be removed from pyomo.common.collections import ComponentMap +from pyomo.common.enums import minimize, maximize from pyomo.core.expr.symbol_map import SymbolMap from pyomo.core.expr.numvalue import ( @@ -33,7 +34,6 @@ BooleanValue, native_logical_values, ) -from pyomo.core.kernel.objective import minimize, maximize from pyomo.core.base.config import PyomoOptions from pyomo.core.base.expression import Expression, _ExpressionData diff --git a/pyomo/core/base/objective.py b/pyomo/core/base/objective.py index fcc63755f2b..10cc853dafb 100644 --- a/pyomo/core/base/objective.py +++ b/pyomo/core/base/objective.py @@ -15,6 +15,7 @@ from pyomo.common.pyomo_typing import overload from pyomo.common.deprecation import RenamedClass +from pyomo.common.enums import ObjectiveSense, minimize, maximize from pyomo.common.log import is_debug_set from pyomo.common.modeling import NOTSET from pyomo.common.formatting import tabular_writer @@ -35,7 +36,6 @@ IndexedCallInitializer, CountedCallInitializer, ) -from pyomo.core.base import minimize, maximize logger = logging.getLogger('pyomo.core') @@ -152,14 +152,7 @@ def __init__(self, expr=None, sense=minimize, component=None): self._component = weakref_ref(component) if (component is not None) else None self._index = NOTSET self._active = True - self._sense = sense - - if (self._sense != minimize) and (self._sense != maximize): - raise ValueError( - "Objective sense must be set to one of " - "'minimize' (%s) or 'maximize' (%s). Invalid " - "value: %s'" % (minimize, maximize, sense) - ) + self._sense = ObjectiveSense(sense) def set_value(self, expr): if expr is None: @@ -182,14 +175,7 @@ def sense(self, sense): def set_sense(self, sense): """Set the sense (direction) of this objective.""" - if sense in {minimize, maximize}: - self._sense = sense - else: - raise ValueError( - "Objective sense must be set to one of " - "'minimize' (%s) or 'maximize' (%s). Invalid " - "value: %s'" % (minimize, maximize, sense) - ) + self._sense = ObjectiveSense(sense) @ModelComponentFactory.register("Expressions that are minimized or maximized.") @@ -353,11 +339,7 @@ def _pprint(self): ], self._data.items(), ("Active", "Sense", "Expression"), - lambda k, v: [ - v.active, - ("minimize" if (v.sense == minimize) else "maximize"), - v.expr, - ], + lambda k, v: [v.active, v.sense, v.expr], ) def display(self, prefix="", ostream=None): diff --git a/pyomo/core/kernel/objective.py b/pyomo/core/kernel/objective.py index 840c7cfd7e0..ac6f22d07d3 100644 --- a/pyomo/core/kernel/objective.py +++ b/pyomo/core/kernel/objective.py @@ -9,7 +9,7 @@ # This software is distributed under the 3-clause BSD License. # ___________________________________________________________________________ -from pyomo.common.enums import minimize, maximize +from pyomo.common.enums import ObjectiveSense, minimize, maximize from pyomo.core.expr.numvalue import as_numeric from pyomo.core.kernel.base import _abstract_readwrite_property from pyomo.core.kernel.container_utils import define_simple_containers @@ -81,14 +81,7 @@ def sense(self): @sense.setter def sense(self, sense): """Set the sense (direction) of this objective.""" - if (sense == minimize) or (sense == maximize): - self._sense = sense - else: - raise ValueError( - "Objective sense must be set to one of: " - "[minimize (%s), maximize (%s)]. Invalid " - "value: %s'" % (minimize, maximize, sense) - ) + self._sense = ObjectiveSense(sense) # inserts class definitions for simple _tuple, _list, and From ab59255c9a574d40a63c8bfdd827efe15b8f7639 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 11:42:00 -0600 Subject: [PATCH 58/83] Remove reserences to ProblemSense --- pyomo/contrib/mindtpy/algorithm_base_class.py | 12 ++---------- pyomo/contrib/mindtpy/util.py | 1 - .../pynumero/algorithms/solvers/cyipopt_solver.py | 5 ++--- pyomo/solvers/plugins/solvers/CBCplugin.py | 12 ++++++------ pyomo/solvers/plugins/solvers/CPLEX.py | 14 +++++++------- pyomo/solvers/plugins/solvers/GAMS.py | 7 ++----- pyomo/solvers/plugins/solvers/GLPK.py | 8 +++----- pyomo/solvers/plugins/solvers/GUROBI.py | 8 ++++---- pyomo/solvers/plugins/solvers/SCIPAMPL.py | 9 ++------- pyomo/solvers/tests/checks/test_CBCplugin.py | 14 +++++++------- 10 files changed, 35 insertions(+), 55 deletions(-) diff --git a/pyomo/contrib/mindtpy/algorithm_base_class.py b/pyomo/contrib/mindtpy/algorithm_base_class.py index 785a89d8982..8c703f8d842 100644 --- a/pyomo/contrib/mindtpy/algorithm_base_class.py +++ b/pyomo/contrib/mindtpy/algorithm_base_class.py @@ -27,13 +27,7 @@ from operator import itemgetter from pyomo.common.errors import DeveloperError from pyomo.solvers.plugins.solvers.gurobi_direct import gurobipy -from pyomo.opt import ( - SolverFactory, - SolverResults, - ProblemSense, - SolutionStatus, - SolverStatus, -) +from pyomo.opt import SolverFactory, SolverResults, SolutionStatus, SolverStatus from pyomo.core import ( minimize, maximize, @@ -633,9 +627,7 @@ def process_objective(self, update_var_con_list=True): raise ValueError('Model has multiple active objectives.') else: main_obj = active_objectives[0] - self.results.problem.sense = ( - ProblemSense.minimize if main_obj.sense == 1 else ProblemSense.maximize - ) + self.results.problem.sense = main_obj.sense self.objective_sense = main_obj.sense # Move the objective to the constraints if it is nonlinear or move_objective is True. diff --git a/pyomo/contrib/mindtpy/util.py b/pyomo/contrib/mindtpy/util.py index 1543497838f..7345af8a3e2 100644 --- a/pyomo/contrib/mindtpy/util.py +++ b/pyomo/contrib/mindtpy/util.py @@ -29,7 +29,6 @@ from pyomo.contrib.mcpp.pyomo_mcpp import mcpp_available, McCormick from pyomo.contrib.fbbt.fbbt import compute_bounds_on_expr import pyomo.core.expr as EXPR -from pyomo.opt import ProblemSense from pyomo.contrib.gdpopt.util import get_main_elapsed_time, time_code from pyomo.util.model_size import build_model_size_report from pyomo.common.dependencies import attempt_import diff --git a/pyomo/contrib/pynumero/algorithms/solvers/cyipopt_solver.py b/pyomo/contrib/pynumero/algorithms/solvers/cyipopt_solver.py index 53616298415..0999550711c 100644 --- a/pyomo/contrib/pynumero/algorithms/solvers/cyipopt_solver.py +++ b/pyomo/contrib/pynumero/algorithms/solvers/cyipopt_solver.py @@ -65,7 +65,7 @@ from pyomo.common.config import ConfigBlock, ConfigValue from pyomo.common.timing import TicTocTimer from pyomo.core.base import Block, Objective, minimize -from pyomo.opt import SolverStatus, SolverResults, TerminationCondition, ProblemSense +from pyomo.opt import SolverStatus, SolverResults, TerminationCondition from pyomo.opt.results.solution import Solution logger = logging.getLogger(__name__) @@ -447,11 +447,10 @@ def solve(self, model, **kwds): results.problem.name = model.name obj = next(model.component_data_objects(Objective, active=True)) + results.problem.sense = obj.sense if obj.sense == minimize: - results.problem.sense = ProblemSense.minimize results.problem.upper_bound = info["obj_val"] else: - results.problem.sense = ProblemSense.maximize results.problem.lower_bound = info["obj_val"] results.problem.number_of_objectives = 1 results.problem.number_of_constraints = ng diff --git a/pyomo/solvers/plugins/solvers/CBCplugin.py b/pyomo/solvers/plugins/solvers/CBCplugin.py index eb6c2c2e1bd..f22fb117c8b 100644 --- a/pyomo/solvers/plugins/solvers/CBCplugin.py +++ b/pyomo/solvers/plugins/solvers/CBCplugin.py @@ -16,6 +16,7 @@ import subprocess from pyomo.common import Executable +from pyomo.common.enums import maximize, minimize from pyomo.common.errors import ApplicationError from pyomo.common.collections import Bunch from pyomo.common.tempfiles import TempfileManager @@ -29,7 +30,6 @@ SolverStatus, TerminationCondition, SolutionStatus, - ProblemSense, Solution, ) from pyomo.opt.solver import SystemCallSolver @@ -443,7 +443,7 @@ def process_logfile(self): # # Parse logfile lines # - results.problem.sense = ProblemSense.minimize + results.problem.sense = minimize results.problem.name = None optim_value = float('inf') lower_bound = None @@ -578,7 +578,7 @@ def process_logfile(self): 'CoinLpIO::readLp(): Maximization problem reformulated as minimization' in ' '.join(tokens) ): - results.problem.sense = ProblemSense.maximize + results.problem.sense = maximize # https://projects.coin-or.org/Cbc/browser/trunk/Cbc/src/CbcSolver.cpp?rev=2497#L3047 elif n_tokens > 3 and tokens[:2] == ('Result', '-'): if tokens[2:4] in [('Run', 'abandoned'), ('User', 'ctrl-c')]: @@ -752,9 +752,9 @@ def process_logfile(self): "maxIterations parameter." ) soln.gap = gap - if results.problem.sense == ProblemSense.minimize: + if results.problem.sense == minimize: upper_bound = optim_value - elif results.problem.sense == ProblemSense.maximize: + elif results.problem.sense == maximize: _ver = self.version() if _ver and _ver[:3] < (2, 10, 2): optim_value *= -1 @@ -824,7 +824,7 @@ def process_soln_file(self, results): INPUT = [] _ver = self.version() - invert_objective_sense = results.problem.sense == ProblemSense.maximize and ( + invert_objective_sense = results.problem.sense == maximize and ( _ver and _ver[:3] < (2, 10, 2) ) diff --git a/pyomo/solvers/plugins/solvers/CPLEX.py b/pyomo/solvers/plugins/solvers/CPLEX.py index 9f876b2d0f8..3a08257c87c 100644 --- a/pyomo/solvers/plugins/solvers/CPLEX.py +++ b/pyomo/solvers/plugins/solvers/CPLEX.py @@ -17,6 +17,7 @@ import subprocess from pyomo.common import Executable +from pyomo.common.enums import maximize, minimize from pyomo.common.errors import ApplicationError from pyomo.common.tempfiles import TempfileManager @@ -28,7 +29,6 @@ SolverStatus, TerminationCondition, SolutionStatus, - ProblemSense, Solution, ) from pyomo.opt.solver import ILMLicensedSystemCallSolver @@ -547,9 +547,9 @@ def process_logfile(self): ): # CPLEX 11.2 and subsequent has two Nonzeros sections. results.problem.number_of_nonzeros = int(tokens[2]) elif len(tokens) >= 5 and tokens[4] == "MINIMIZE": - results.problem.sense = ProblemSense.minimize + results.problem.sense = minimize elif len(tokens) >= 5 and tokens[4] == "MAXIMIZE": - results.problem.sense = ProblemSense.maximize + results.problem.sense = maximize elif ( len(tokens) >= 4 and tokens[0] == "Solution" @@ -859,9 +859,9 @@ def process_soln_file(self, results): else: sense = tokens[0].lower() if sense in ['max', 'maximize']: - results.problem.sense = ProblemSense.maximize + results.problem.sense = maximize if sense in ['min', 'minimize']: - results.problem.sense = ProblemSense.minimize + results.problem.sense = minimize break tINPUT.close() @@ -952,7 +952,7 @@ def process_soln_file(self, results): ) if primal_feasible == 1: soln.status = SolutionStatus.feasible - if results.problem.sense == ProblemSense.minimize: + if results.problem.sense == minimize: results.problem.upper_bound = soln.objective[ '__default_objective__' ]['Value'] @@ -964,7 +964,7 @@ def process_soln_file(self, results): soln.status = SolutionStatus.infeasible if self._best_bound is not None: - if results.problem.sense == ProblemSense.minimize: + if results.problem.sense == minimize: results.problem.lower_bound = self._best_bound else: results.problem.upper_bound = self._best_bound diff --git a/pyomo/solvers/plugins/solvers/GAMS.py b/pyomo/solvers/plugins/solvers/GAMS.py index c0bab4dc23e..035bd0b7603 100644 --- a/pyomo/solvers/plugins/solvers/GAMS.py +++ b/pyomo/solvers/plugins/solvers/GAMS.py @@ -36,7 +36,6 @@ Solution, SolutionStatus, TerminationCondition, - ProblemSense, ) from pyomo.common.dependencies import attempt_import @@ -422,11 +421,10 @@ def solve(self, *args, **kwds): assert len(obj) == 1, 'Only one objective is allowed.' obj = obj[0] objctvval = t1.out_db["OBJVAL"].find_record().value + results.problem.sense = obj.sense if obj.is_minimizing(): - results.problem.sense = ProblemSense.minimize results.problem.upper_bound = objctvval else: - results.problem.sense = ProblemSense.maximize results.problem.lower_bound = objctvval results.solver.name = "GAMS " + str(self.version()) @@ -984,11 +982,10 @@ def solve(self, *args, **kwds): assert len(obj) == 1, 'Only one objective is allowed.' obj = obj[0] objctvval = stat_vars["OBJVAL"] + results.problem.sense = obj.sense if obj.is_minimizing(): - results.problem.sense = ProblemSense.minimize results.problem.upper_bound = objctvval else: - results.problem.sense = ProblemSense.maximize results.problem.lower_bound = objctvval results.solver.name = "GAMS " + str(self.version()) diff --git a/pyomo/solvers/plugins/solvers/GLPK.py b/pyomo/solvers/plugins/solvers/GLPK.py index e6d8576489d..c8d5bc14237 100644 --- a/pyomo/solvers/plugins/solvers/GLPK.py +++ b/pyomo/solvers/plugins/solvers/GLPK.py @@ -19,6 +19,7 @@ from pyomo.common import Executable from pyomo.common.collections import Bunch +from pyomo.common.enums import maximize, minimize from pyomo.common.errors import ApplicationError from pyomo.opt import ( SolverFactory, @@ -28,7 +29,6 @@ SolverResults, TerminationCondition, SolutionStatus, - ProblemSense, ) from pyomo.opt.base.solvers import _extract_version from pyomo.opt.solver import SystemCallSolver @@ -308,10 +308,8 @@ def process_soln_file(self, results): ): raise ValueError - self.is_integer = 'mip' == ptype and True or False - prob.sense = ( - 'min' == psense and ProblemSense.minimize or ProblemSense.maximize - ) + self.is_integer = 'mip' == ptype + prob.sense = minimize if 'min' == psense else maximize prob.number_of_constraints = prows prob.number_of_nonzeros = pnonz prob.number_of_variables = pcols diff --git a/pyomo/solvers/plugins/solvers/GUROBI.py b/pyomo/solvers/plugins/solvers/GUROBI.py index c8b0912970e..3a3a4d52322 100644 --- a/pyomo/solvers/plugins/solvers/GUROBI.py +++ b/pyomo/solvers/plugins/solvers/GUROBI.py @@ -18,6 +18,7 @@ from pyomo.common import Executable from pyomo.common.collections import Bunch +from pyomo.common.enums import maximize, minimize from pyomo.common.fileutils import this_file_dir from pyomo.common.tee import capture_output from pyomo.common.tempfiles import TempfileManager @@ -28,7 +29,6 @@ SolverStatus, TerminationCondition, SolutionStatus, - ProblemSense, Solution, ) from pyomo.opt.solver import ILMLicensedSystemCallSolver @@ -472,7 +472,7 @@ def process_soln_file(self, results): soln.objective['__default_objective__'] = { 'Value': float(tokens[1]) } - if results.problem.sense == ProblemSense.minimize: + if results.problem.sense == minimize: results.problem.upper_bound = float(tokens[1]) else: results.problem.lower_bound = float(tokens[1]) @@ -514,9 +514,9 @@ def process_soln_file(self, results): elif section == 1: if tokens[0] == 'sense': if tokens[1] == 'minimize': - results.problem.sense = ProblemSense.minimize + results.problem.sense = minimize elif tokens[1] == 'maximize': - results.problem.sense = ProblemSense.maximize + results.problem.sense = maximize else: try: val = eval(tokens[1]) diff --git a/pyomo/solvers/plugins/solvers/SCIPAMPL.py b/pyomo/solvers/plugins/solvers/SCIPAMPL.py index fd69954b428..6940ad7b5fe 100644 --- a/pyomo/solvers/plugins/solvers/SCIPAMPL.py +++ b/pyomo/solvers/plugins/solvers/SCIPAMPL.py @@ -20,12 +20,7 @@ from pyomo.opt.base import ProblemFormat, ResultsFormat from pyomo.opt.base.solvers import _extract_version, SolverFactory -from pyomo.opt.results import ( - SolverStatus, - TerminationCondition, - SolutionStatus, - ProblemSense, -) +from pyomo.opt.results import SolverStatus, TerminationCondition, SolutionStatus from pyomo.opt.solver import SystemCallSolver import logging @@ -374,7 +369,7 @@ def _postsolve(self): if len(results.solution) > 0: results.solution(0).status = SolutionStatus.optimal try: - if results.problem.sense == ProblemSense.minimize: + if results.solver.primal_bound < results.solver.dual_bound: results.problem.lower_bound = results.solver.primal_bound else: results.problem.upper_bound = results.solver.primal_bound diff --git a/pyomo/solvers/tests/checks/test_CBCplugin.py b/pyomo/solvers/tests/checks/test_CBCplugin.py index 2ea0e55c5f4..ad8846509ea 100644 --- a/pyomo/solvers/tests/checks/test_CBCplugin.py +++ b/pyomo/solvers/tests/checks/test_CBCplugin.py @@ -29,7 +29,7 @@ maximize, minimize, ) -from pyomo.opt import SolverFactory, ProblemSense, TerminationCondition, SolverStatus +from pyomo.opt import SolverFactory, TerminationCondition, SolverStatus from pyomo.solvers.plugins.solvers.CBCplugin import CBCSHELL cbc_available = SolverFactory('cbc', solver_io='lp').available(exception_flag=False) @@ -62,7 +62,7 @@ def test_infeasible_lp(self): results = self.opt.solve(self.model) - self.assertEqual(ProblemSense.minimize, results.problem.sense) + self.assertEqual(minimize, results.problem.sense) self.assertEqual( TerminationCondition.infeasible, results.solver.termination_condition ) @@ -81,7 +81,7 @@ def test_unbounded_lp(self): results = self.opt.solve(self.model) - self.assertEqual(ProblemSense.maximize, results.problem.sense) + self.assertEqual(maximize, results.problem.sense) self.assertEqual( TerminationCondition.unbounded, results.solver.termination_condition ) @@ -99,7 +99,7 @@ def test_optimal_lp(self): self.assertEqual(0.0, results.problem.lower_bound) self.assertEqual(0.0, results.problem.upper_bound) - self.assertEqual(ProblemSense.minimize, results.problem.sense) + self.assertEqual(minimize, results.problem.sense) self.assertEqual( TerminationCondition.optimal, results.solver.termination_condition ) @@ -118,7 +118,7 @@ def test_infeasible_mip(self): results = self.opt.solve(self.model) - self.assertEqual(ProblemSense.minimize, results.problem.sense) + self.assertEqual(minimize, results.problem.sense) self.assertEqual( TerminationCondition.infeasible, results.solver.termination_condition ) @@ -134,7 +134,7 @@ def test_unbounded_mip(self): results = self.opt.solve(self.model) - self.assertEqual(ProblemSense.minimize, results.problem.sense) + self.assertEqual(minimize, results.problem.sense) self.assertEqual( TerminationCondition.unbounded, results.solver.termination_condition ) @@ -159,7 +159,7 @@ def test_optimal_mip(self): self.assertEqual(1.0, results.problem.upper_bound) self.assertEqual(results.problem.number_of_binary_variables, 2) self.assertEqual(results.problem.number_of_integer_variables, 4) - self.assertEqual(ProblemSense.maximize, results.problem.sense) + self.assertEqual(maximize, results.problem.sense) self.assertEqual( TerminationCondition.optimal, results.solver.termination_condition ) From f80ff256c0da8a65f8be956e011246dc16f15583 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 11:44:22 -0600 Subject: [PATCH 59/83] Report both lower and upper bounds from SCIP --- pyomo/solvers/plugins/solvers/SCIPAMPL.py | 2 ++ pyomo/solvers/tests/mip/test_scip_solve_from_instance.baseline | 2 +- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/pyomo/solvers/plugins/solvers/SCIPAMPL.py b/pyomo/solvers/plugins/solvers/SCIPAMPL.py index 6940ad7b5fe..c309ad29d96 100644 --- a/pyomo/solvers/plugins/solvers/SCIPAMPL.py +++ b/pyomo/solvers/plugins/solvers/SCIPAMPL.py @@ -371,7 +371,9 @@ def _postsolve(self): try: if results.solver.primal_bound < results.solver.dual_bound: results.problem.lower_bound = results.solver.primal_bound + results.problem.upper_bound = results.solver.dual_bound else: + results.problem.lower_bound = results.solver.dual_bound results.problem.upper_bound = results.solver.primal_bound except AttributeError: """ diff --git a/pyomo/solvers/tests/mip/test_scip_solve_from_instance.baseline b/pyomo/solvers/tests/mip/test_scip_solve_from_instance.baseline index a3eb9ffacec..976e4a1b82e 100644 --- a/pyomo/solvers/tests/mip/test_scip_solve_from_instance.baseline +++ b/pyomo/solvers/tests/mip/test_scip_solve_from_instance.baseline @@ -1,7 +1,7 @@ { "Problem": [ { - "Lower bound": -Infinity, + "Lower bound": 1.0, "Number of constraints": 0, "Number of objectives": 1, "Number of variables": 1, From 2f59e44f0eb0e1f360ee41fd3daebaba3404f7c3 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 12:26:12 -0600 Subject: [PATCH 60/83] Updating baselines; ironically this makes the expected output actually match what is advertised in the Book --- examples/pyomobook/pyomo-components-ch/obj_declaration.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/examples/pyomobook/pyomo-components-ch/obj_declaration.txt b/examples/pyomobook/pyomo-components-ch/obj_declaration.txt index 607586a1fb3..e4d4b02a252 100644 --- a/examples/pyomobook/pyomo-components-ch/obj_declaration.txt +++ b/examples/pyomobook/pyomo-components-ch/obj_declaration.txt @@ -55,7 +55,7 @@ Model unknown None value x[Q] + 2*x[R] -1 +minimize 6.5 Model unknown From e1ad8e55b1b8ce26a4695f275b371f67c18062a8 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 13:04:43 -0600 Subject: [PATCH 61/83] Adding portability fixes for Python<3.11 --- pyomo/common/enums.py | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/pyomo/common/enums.py b/pyomo/common/enums.py index 7f00e87a85f..ee934acd35f 100644 --- a/pyomo/common/enums.py +++ b/pyomo/common/enums.py @@ -11,9 +11,14 @@ import enum import itertools +import sys +if sys.version_info[:2] < (3, 11): + _EnumType = enum.EnumMeta +else: + _EnumType = enum.EnumType -class ExtendedEnumType(enum.EnumType): +class ExtendedEnumType(_EnumType): """Metaclass for creating an :py:class:`Enum` that extends another Enum In general, :py:class:`Enum` classes are not extensible: that is, From 4aa861cef0c91a5d335cb83d358a8ecf0074fb3c Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 13:50:58 -0600 Subject: [PATCH 62/83] NFC: apply black --- pyomo/common/enums.py | 1 + 1 file changed, 1 insertion(+) diff --git a/pyomo/common/enums.py b/pyomo/common/enums.py index ee934acd35f..7de8b13b81f 100644 --- a/pyomo/common/enums.py +++ b/pyomo/common/enums.py @@ -18,6 +18,7 @@ else: _EnumType = enum.EnumType + class ExtendedEnumType(_EnumType): """Metaclass for creating an :py:class:`Enum` that extends another Enum From d095e2409ded5cc027fa50e0b07b5bb17b77c06f Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 15:14:10 -0600 Subject: [PATCH 63/83] Integrate common.enums into online docs --- .../library_reference/common/enums.rst | 7 +++++ .../library_reference/common/index.rst | 1 + pyomo/common/enums.py | 26 +++++++++++++++++-- 3 files changed, 32 insertions(+), 2 deletions(-) create mode 100644 doc/OnlineDocs/library_reference/common/enums.rst diff --git a/doc/OnlineDocs/library_reference/common/enums.rst b/doc/OnlineDocs/library_reference/common/enums.rst new file mode 100644 index 00000000000..5ed2dbb1e80 --- /dev/null +++ b/doc/OnlineDocs/library_reference/common/enums.rst @@ -0,0 +1,7 @@ + +pyomo.common.enums +================== + +.. automodule:: pyomo.common.enums + :members: + :member-order: bysource diff --git a/doc/OnlineDocs/library_reference/common/index.rst b/doc/OnlineDocs/library_reference/common/index.rst index c9c99008250..c03436600f2 100644 --- a/doc/OnlineDocs/library_reference/common/index.rst +++ b/doc/OnlineDocs/library_reference/common/index.rst @@ -11,6 +11,7 @@ or rely on any other parts of Pyomo. config.rst dependencies.rst deprecation.rst + enums.rst errors.rst fileutils.rst formatting.rst diff --git a/pyomo/common/enums.py b/pyomo/common/enums.py index 7de8b13b81f..9988beedbff 100644 --- a/pyomo/common/enums.py +++ b/pyomo/common/enums.py @@ -9,6 +9,23 @@ # This software is distributed under the 3-clause BSD License. # ___________________________________________________________________________ +"""This module provides standard :py:class:`enum.Enum` definitions used in +Pyomo, along with additional utilities for working with custom Enums + +Utilities: + +.. autosummary:: + + ExtendedEnumType + +Standard Enums: + +.. autosummary:: + + ObjectiveSense + +""" + import enum import itertools import sys @@ -20,9 +37,9 @@ class ExtendedEnumType(_EnumType): - """Metaclass for creating an :py:class:`Enum` that extends another Enum + """Metaclass for creating an :py:class:`enum.Enum` that extends another Enum - In general, :py:class:`Enum` classes are not extensible: that is, + In general, :py:class:`enum.Enum` classes are not extensible: that is, they are frozen when defined and cannot be the base class of another Enum. This Metaclass provides a workaround for creating a new Enum that extends an existing enum. Members in the base Enum are all @@ -84,6 +101,11 @@ def __iter__(cls): # the local members return itertools.chain(super().__iter__(), cls.__base_enum__.__iter__()) + def __contains__(cls, member): + # This enum "containts" both it's local members and the members + # in the __base_enum__ (necessary for good auto-enum[sphinx] docs) + return super().__contains__(member) or member in cls.__base_enum__ + def __instancecheck__(cls, instance): if cls.__subclasscheck__(type(instance)): return True From f6b4ea93e8c25cd6b535051b0177c4620162a499 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 15:33:20 -0600 Subject: [PATCH 64/83] Add unit tests --- pyomo/common/enums.py | 4 +- pyomo/common/tests/test_enums.py | 99 ++++++++++++++++++++++++++++++++ 2 files changed, 101 insertions(+), 2 deletions(-) create mode 100644 pyomo/common/tests/test_enums.py diff --git a/pyomo/common/enums.py b/pyomo/common/enums.py index 9988beedbff..0dd65829026 100644 --- a/pyomo/common/enums.py +++ b/pyomo/common/enums.py @@ -83,10 +83,10 @@ class ProblemSense(enum.IntEnum, metaclass=ExtendedEnumType): >>> hasattr(ProblemSense, 'minimize') True - >>> hasattr(ProblemSense, 'unknown') - True >>> ProblemSense.minimize is ObjectiveSense.minimize True + >>> ProblemSense.minimize in ProblemSense + True """ diff --git a/pyomo/common/tests/test_enums.py b/pyomo/common/tests/test_enums.py new file mode 100644 index 00000000000..2d5ab01b6e3 --- /dev/null +++ b/pyomo/common/tests/test_enums.py @@ -0,0 +1,99 @@ +# ___________________________________________________________________________ +# +# Pyomo: Python Optimization Modeling Objects +# Copyright (c) 2008-2024 +# National Technology and Engineering Solutions of Sandia, LLC +# Under the terms of Contract DE-NA0003525 with National Technology and +# Engineering Solutions of Sandia, LLC, the U.S. Government retains certain +# rights in this software. +# This software is distributed under the 3-clause BSD License. +# ___________________________________________________________________________ + +import enum + +import pyomo.common.unittest as unittest + +from pyomo.common.enums import ExtendedEnumType, ObjectiveSense + + +class ProblemSense(enum.IntEnum, metaclass=ExtendedEnumType): + __base_enum__ = ObjectiveSense + + unknown = 0 + + +class TestExtendedEnumType(unittest.TestCase): + def test_members(self): + self.assertEqual( + list(ProblemSense), + [ProblemSense.unknown, ObjectiveSense.minimize, ObjectiveSense.maximize], + ) + + def test_isinstance(self): + self.assertIsInstance(ProblemSense.unknown, ProblemSense) + self.assertIsInstance(ProblemSense.minimize, ProblemSense) + self.assertIsInstance(ProblemSense.maximize, ProblemSense) + + self.assertTrue(ProblemSense.__instancecheck__(ProblemSense.unknown)) + self.assertTrue(ProblemSense.__instancecheck__(ProblemSense.minimize)) + self.assertTrue(ProblemSense.__instancecheck__(ProblemSense.maximize)) + + def test_getattr(self): + self.assertIs(ProblemSense.unknown, ProblemSense.unknown) + self.assertIs(ProblemSense.minimize, ObjectiveSense.minimize) + self.assertIs(ProblemSense.maximize, ObjectiveSense.maximize) + + def test_hasattr(self): + self.assertTrue(hasattr(ProblemSense, 'unknown')) + self.assertTrue(hasattr(ProblemSense, 'minimize')) + self.assertTrue(hasattr(ProblemSense, 'maximize')) + + def test_call(self): + self.assertIs(ProblemSense(0), ProblemSense.unknown) + self.assertIs(ProblemSense(1), ObjectiveSense.minimize) + self.assertIs(ProblemSense(-1), ObjectiveSense.maximize) + + self.assertIs(ProblemSense('unknown'), ProblemSense.unknown) + self.assertIs(ProblemSense('minimize'), ObjectiveSense.minimize) + self.assertIs(ProblemSense('maximize'), ObjectiveSense.maximize) + + with self.assertRaisesRegex( + ValueError, "'foo' is not a valid ProblemSense" + ): + ProblemSense('foo') + + def test_contains(self): + self.assertIn(ProblemSense.unknown, ProblemSense) + self.assertIn(ProblemSense.minimize, ProblemSense) + self.assertIn(ProblemSense.maximize, ProblemSense) + + self.assertNotIn(ProblemSense.unknown, ObjectiveSense) + self.assertIn(ProblemSense.minimize, ObjectiveSense) + self.assertIn(ProblemSense.maximize, ObjectiveSense) + +class TestObjectiveSense(unittest.TestCase): + def test_members(self): + self.assertEqual( + list(ObjectiveSense), + [ObjectiveSense.minimize, ObjectiveSense.maximize], + ) + + def test_hasattr(self): + self.assertTrue(hasattr(ProblemSense, 'minimize')) + self.assertTrue(hasattr(ProblemSense, 'maximize')) + + def test_call(self): + self.assertIs(ObjectiveSense(1), ObjectiveSense.minimize) + self.assertIs(ObjectiveSense(-1), ObjectiveSense.maximize) + + self.assertIs(ObjectiveSense('minimize'), ObjectiveSense.minimize) + self.assertIs(ObjectiveSense('maximize'), ObjectiveSense.maximize) + + with self.assertRaisesRegex( + ValueError, "'foo' is not a valid ObjectiveSense" + ): + ObjectiveSense('foo') + + def test_str(self): + self.assertEqual(str(ObjectiveSense.minimize), 'minimize') + self.assertEqual(str(ObjectiveSense.maximize), 'maximize') From 98c960e937cdd30b1f7be2d5d00387a90fbe99af Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 15:39:27 -0600 Subject: [PATCH 65/83] NFC: fix typos --- pyomo/common/enums.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/pyomo/common/enums.py b/pyomo/common/enums.py index 0dd65829026..4d969bf7a9e 100644 --- a/pyomo/common/enums.py +++ b/pyomo/common/enums.py @@ -102,8 +102,8 @@ def __iter__(cls): return itertools.chain(super().__iter__(), cls.__base_enum__.__iter__()) def __contains__(cls, member): - # This enum "containts" both it's local members and the members - # in the __base_enum__ (necessary for good auto-enum[sphinx] docs) + # This enum "contains" both its local members and the members in + # the __base_enum__ (necessary for good auto-enum[sphinx] docs) return super().__contains__(member) or member in cls.__base_enum__ def __instancecheck__(cls, instance): @@ -124,7 +124,7 @@ def _missing_(cls, value): def __new__(metacls, cls, bases, classdict, **kwds): # Support lookup by name - but only if the new Enum doesn't - # specify it's own implementation of _missing_ + # specify its own implementation of _missing_ if '_missing_' not in classdict: classdict['_missing_'] = classmethod(ExtendedEnumType._missing_) return super().__new__(metacls, cls, bases, classdict, **kwds) From 6c3245310aadd3211c2c7120d293adfb135517e2 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 3 Apr 2024 15:40:45 -0600 Subject: [PATCH 66/83] NFC: apply black --- pyomo/common/tests/test_enums.py | 12 ++++-------- 1 file changed, 4 insertions(+), 8 deletions(-) diff --git a/pyomo/common/tests/test_enums.py b/pyomo/common/tests/test_enums.py index 2d5ab01b6e3..52ee1c5abb3 100644 --- a/pyomo/common/tests/test_enums.py +++ b/pyomo/common/tests/test_enums.py @@ -57,9 +57,7 @@ def test_call(self): self.assertIs(ProblemSense('minimize'), ObjectiveSense.minimize) self.assertIs(ProblemSense('maximize'), ObjectiveSense.maximize) - with self.assertRaisesRegex( - ValueError, "'foo' is not a valid ProblemSense" - ): + with self.assertRaisesRegex(ValueError, "'foo' is not a valid ProblemSense"): ProblemSense('foo') def test_contains(self): @@ -71,11 +69,11 @@ def test_contains(self): self.assertIn(ProblemSense.minimize, ObjectiveSense) self.assertIn(ProblemSense.maximize, ObjectiveSense) + class TestObjectiveSense(unittest.TestCase): def test_members(self): self.assertEqual( - list(ObjectiveSense), - [ObjectiveSense.minimize, ObjectiveSense.maximize], + list(ObjectiveSense), [ObjectiveSense.minimize, ObjectiveSense.maximize] ) def test_hasattr(self): @@ -89,9 +87,7 @@ def test_call(self): self.assertIs(ObjectiveSense('minimize'), ObjectiveSense.minimize) self.assertIs(ObjectiveSense('maximize'), ObjectiveSense.maximize) - with self.assertRaisesRegex( - ValueError, "'foo' is not a valid ObjectiveSense" - ): + with self.assertRaisesRegex(ValueError, "'foo' is not a valid ObjectiveSense"): ObjectiveSense('foo') def test_str(self): From 5dac102e6391311ff7a5615b870199dc3776842a Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 4 Apr 2024 17:13:34 -0600 Subject: [PATCH 67/83] Adding test requested by PR review --- pyomo/common/tests/test_enums.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/pyomo/common/tests/test_enums.py b/pyomo/common/tests/test_enums.py index 52ee1c5abb3..80d081505e9 100644 --- a/pyomo/common/tests/test_enums.py +++ b/pyomo/common/tests/test_enums.py @@ -59,6 +59,8 @@ def test_call(self): with self.assertRaisesRegex(ValueError, "'foo' is not a valid ProblemSense"): ProblemSense('foo') + with self.assertRaisesRegex(ValueError, "2 is not a valid ProblemSense"): + ProblemSense(2) def test_contains(self): self.assertIn(ProblemSense.unknown, ProblemSense) From 88535d42141f0aa678ec88b8a86cf23684faf9aa Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 10 Apr 2024 09:24:12 -0600 Subject: [PATCH 68/83] Remove remaining references to '_.*Data' classes --- pyomo/contrib/pyros/config.py | 2 +- pyomo/core/base/block.py | 18 +++++++++--------- pyomo/gdp/util.py | 2 +- 3 files changed, 11 insertions(+), 11 deletions(-) diff --git a/pyomo/contrib/pyros/config.py b/pyomo/contrib/pyros/config.py index 59bf9a9ab37..31e462223da 100644 --- a/pyomo/contrib/pyros/config.py +++ b/pyomo/contrib/pyros/config.py @@ -98,7 +98,7 @@ class InputDataStandardizer(object): Pyomo component type, such as Component, Var or Param. cdatatype : type Corresponding Pyomo component data type, such as - _ComponentData, VarData, or ParamData. + ComponentData, VarData, or ParamData. ctype_validator : callable, optional Validator function for objects of type `ctype`. cdatatype_validator : callable, optional diff --git a/pyomo/core/base/block.py b/pyomo/core/base/block.py index 8f4e86fe697..3eb18dde7a9 100644 --- a/pyomo/core/base/block.py +++ b/pyomo/core/base/block.py @@ -160,13 +160,13 @@ def __init__(self): self.seen_data = set() def unique(self, comp, items, are_values): - """Returns generator that filters duplicate _ComponentData objects from items + """Returns generator that filters duplicate ComponentData objects from items Parameters ---------- comp: ComponentBase The Component (indexed or scalar) that contains all - _ComponentData returned by the `items` generator. `comp` may + ComponentData returned by the `items` generator. `comp` may be an IndexedComponent generated by :py:func:`Reference` (and hence may not own the component datas in `items`) @@ -175,8 +175,8 @@ def unique(self, comp, items, are_values): `comp` Component. are_values: bool - If `True`, `items` yields _ComponentData objects, otherwise, - `items` yields `(index, _ComponentData)` tuples. + If `True`, `items` yields ComponentData objects, otherwise, + `items` yields `(index, ComponentData)` tuples. """ if comp.is_reference(): @@ -1399,7 +1399,7 @@ def _component_data_iteritems(self, ctype, active, sort, dedup): Generator that returns a nested 2-tuple of - ((component name, index value), _ComponentData) + ((component name, index value), ComponentData) for every component data in the block matching the specified ctype(s). @@ -1416,7 +1416,7 @@ def _component_data_iteritems(self, ctype, active, sort, dedup): Iterate over the components in a specified sorted order dedup: _DeduplicateInfo - Deduplicator to prevent returning the same _ComponentData twice + Deduplicator to prevent returning the same ComponentData twice """ for name, comp in PseudoMap(self, ctype, active, sort).items(): # NOTE: Suffix has a dict interface (something other derived @@ -1452,7 +1452,7 @@ def _component_data_iteritems(self, ctype, active, sort, dedup): yield from dedup.unique(comp, _items, False) def _component_data_itervalues(self, ctype, active, sort, dedup): - """Generator that returns the _ComponentData for every component data + """Generator that returns the ComponentData for every component data in the block. Parameters @@ -1467,7 +1467,7 @@ def _component_data_itervalues(self, ctype, active, sort, dedup): Iterate over the components in a specified sorted order dedup: _DeduplicateInfo - Deduplicator to prevent returning the same _ComponentData twice + Deduplicator to prevent returning the same ComponentData twice """ for comp in PseudoMap(self, ctype, active, sort).values(): # NOTE: Suffix has a dict interface (something other derived @@ -1573,7 +1573,7 @@ def component_data_iterindex( generator recursively descends into sub-blocks. The tuple is - ((component name, index value), _ComponentData) + ((component name, index value), ComponentData) """ dedup = _DeduplicateInfo() diff --git a/pyomo/gdp/util.py b/pyomo/gdp/util.py index ee905791c26..2fe8e9e1dee 100644 --- a/pyomo/gdp/util.py +++ b/pyomo/gdp/util.py @@ -534,7 +534,7 @@ def get_transformed_constraints(srcConstraint): "want the container for all transformed constraints " "from an IndexedDisjunction, this is the parent " "component of a transformed constraint originating " - "from any of its _ComponentDatas.)" + "from any of its ComponentDatas.)" ) transBlock = _get_constraint_transBlock(srcConstraint) transformed_constraints = transBlock.private_data( From b235295174500eacb3bc0c2171d298b3ce3b8d48 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 10 Apr 2024 09:31:02 -0600 Subject: [PATCH 69/83] calculate_variable_from_constraint: add check for indexed constraint --- pyomo/util/calc_var_value.py | 7 +++++++ pyomo/util/tests/test_calc_var_value.py | 9 +++++++++ 2 files changed, 16 insertions(+) diff --git a/pyomo/util/calc_var_value.py b/pyomo/util/calc_var_value.py index 156ad56dffb..42ee3119361 100644 --- a/pyomo/util/calc_var_value.py +++ b/pyomo/util/calc_var_value.py @@ -85,6 +85,13 @@ def calculate_variable_from_constraint( constraint = Constraint(expr=constraint, name=type(constraint).__name__) constraint.construct() + if constraint.is_indexed(): + raise ValueError( + 'calculate_variable_from_constraint(): constraint must be a ' + 'scalar constraint or a single ConstraintData. Received ' + f'{constraint.__class__.__name__} ("{constraint.name}")' + ) + body = constraint.body lower = constraint.lb upper = constraint.ub diff --git a/pyomo/util/tests/test_calc_var_value.py b/pyomo/util/tests/test_calc_var_value.py index a02d7a7d838..4bed4d5c843 100644 --- a/pyomo/util/tests/test_calc_var_value.py +++ b/pyomo/util/tests/test_calc_var_value.py @@ -101,6 +101,15 @@ def test_initialize_value(self): ): calculate_variable_from_constraint(m.x, m.lt) + m.indexed = Constraint([1, 2], rule=lambda m, i: m.x <= i) + with self.assertRaisesRegex( + ValueError, + r"calculate_variable_from_constraint\(\): constraint must be a scalar " + r"constraint or a single ConstraintData. Received IndexedConstraint " + r'\("indexed"\)', + ): + calculate_variable_from_constraint(m.x, m.indexed) + def test_linear(self): m = ConcreteModel() m.x = Var() From 76cd7469b5faeb970ccf5b62e7f7e85e6c96cabd Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 10 Apr 2024 09:44:42 -0600 Subject: [PATCH 70/83] NFC: Update docstring to fix typo and copy/paste errors --- pyomo/core/base/boolean_var.py | 44 ++++++++++++++++++---------------- 1 file changed, 24 insertions(+), 20 deletions(-) diff --git a/pyomo/core/base/boolean_var.py b/pyomo/core/base/boolean_var.py index 98761dee536..67c06bdacce 100644 --- a/pyomo/core/base/boolean_var.py +++ b/pyomo/core/base/boolean_var.py @@ -81,26 +81,30 @@ def _associated_binary_mapper(encode, val): class BooleanVarData(ComponentData, BooleanValue): - """ - This class defines the data for a single Boolean variable. - - Constructor Arguments: - component The BooleanVar object that owns this data. - - Public Class Attributes: - domain The domain of this variable. - fixed If True, then this variable is treated as a - fixed constant in the model. - stale A Boolean indicating whether the value of this variable is - legitimiate. This value is true if the value should - be considered legitimate for purposes of reporting or - other interrogation. - value The numeric value of this variable. - - The domain attribute is a property because it is - too widely accessed directly to enforce explicit getter/setter - methods and we need to deter directly modifying or accessing - these attributes in certain cases. + """This class defines the data for a single Boolean variable. + + Parameters + ---------- + component: Component + The BooleanVar object that owns this data. + + Attributes + ---------- + domain: SetData + The domain of this variable. + + fixed: bool + If True, then this variable is treated as a fixed constant in + the model. + + stale: bool + A Boolean indicating whether the value of this variable is + Consistent with the most recent solve. `True` indicates that + this variable's value was set prior to the most recent solve and + was not updated by the results returned by the solve. + + value: bool + The value of this variable. """ __slots__ = ('_value', 'fixed', '_stale', '_associated_binary') From 13830955da64e801bd61a583582783e48243c742 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 18 Apr 2024 08:47:04 -0600 Subject: [PATCH 71/83] Remove unused import --- pyomo/opt/results/problem.py | 1 - 1 file changed, 1 deletion(-) diff --git a/pyomo/opt/results/problem.py b/pyomo/opt/results/problem.py index 34da8f91918..a8eca1e3b41 100644 --- a/pyomo/opt/results/problem.py +++ b/pyomo/opt/results/problem.py @@ -12,7 +12,6 @@ import enum from pyomo.opt.results.container import MapContainer -from pyomo.common.deprecation import deprecated, deprecation_warning from pyomo.common.enums import ExtendedEnumType, ObjectiveSense From 232be203e8669d174b6aaa97ecfa0ddd1d639eeb Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 18 Apr 2024 09:52:27 -0600 Subject: [PATCH 72/83] Remove duplicate imports --- pyomo/core/base/__init__.py | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/pyomo/core/base/__init__.py b/pyomo/core/base/__init__.py index 3d1347659db..341af677b0e 100644 --- a/pyomo/core/base/__init__.py +++ b/pyomo/core/base/__init__.py @@ -84,7 +84,6 @@ from pyomo.core.base.boolean_var import ( BooleanVar, BooleanVarData, - BooleanVarData, BooleanVarList, ScalarBooleanVar, ) @@ -145,7 +144,7 @@ active_import_suffix_generator, Suffix, ) -from pyomo.core.base.var import Var, VarData, VarData, ScalarVar, VarList +from pyomo.core.base.var import Var, VarData, ScalarVar, VarList from pyomo.core.base.instance2dat import instance2dat From 354cadf178d6210ebe386687ff1af15d8481c253 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 18 Apr 2024 09:53:00 -0600 Subject: [PATCH 73/83] Revert accidental test name change --- pyomo/core/tests/unit/test_suffix.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/pyomo/core/tests/unit/test_suffix.py b/pyomo/core/tests/unit/test_suffix.py index 70f028a3eff..d2e861cceb5 100644 --- a/pyomo/core/tests/unit/test_suffix.py +++ b/pyomo/core/tests/unit/test_suffix.py @@ -1567,7 +1567,7 @@ def test_clone_ObjectiveArray(self): self.assertEqual(inst.junk.get(model.obj[1]), None) self.assertEqual(inst.junk.get(inst.obj[1]), 1.0) - def test_cloneObjectiveData(self): + def test_clone_ObjectiveData(self): model = ConcreteModel() model.x = Var([1, 2, 3], dense=True) model.obj = Objective([1, 2, 3], rule=lambda model, i: model.x[i]) @@ -1603,7 +1603,7 @@ def test_clone_IndexedBlock(self): self.assertEqual(inst.junk.get(model.b[1]), None) self.assertEqual(inst.junk.get(inst.b[1]), 1.0) - def test_cloneBlockData(self): + def test_clone_BlockData(self): model = ConcreteModel() model.b = Block([1, 2, 3]) model.junk = Suffix() @@ -1725,7 +1725,7 @@ def test_pickle_ObjectiveArray(self): self.assertEqual(inst.junk.get(model.obj[1]), None) self.assertEqual(inst.junk.get(inst.obj[1]), 1.0) - def test_pickleObjectiveData(self): + def test_pickle_ObjectiveData(self): model = ConcreteModel() model.x = Var([1, 2, 3], dense=True) model.obj = Objective([1, 2, 3], rule=simple_obj_rule) @@ -1761,7 +1761,7 @@ def test_pickle_IndexedBlock(self): self.assertEqual(inst.junk.get(model.b[1]), None) self.assertEqual(inst.junk.get(inst.b[1]), 1.0) - def test_pickleBlockData(self): + def test_pickle_BlockData(self): model = ConcreteModel() model.b = Block([1, 2, 3]) model.junk = Suffix() From 37915b4b409c3e468d70e0ed64faaee0b7c83ef5 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 18 Apr 2024 09:53:59 -0600 Subject: [PATCH 74/83] Fix docstring, add Objectives as known type to FBBT --- pyomo/contrib/fbbt/fbbt.py | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/pyomo/contrib/fbbt/fbbt.py b/pyomo/contrib/fbbt/fbbt.py index eb7155313c4..1507c4a3cc5 100644 --- a/pyomo/contrib/fbbt/fbbt.py +++ b/pyomo/contrib/fbbt/fbbt.py @@ -24,9 +24,10 @@ import math from pyomo.core.base.block import Block from pyomo.core.base.constraint import Constraint +from pyomo.core.base.expression import ExpressionData, ScalarExpression +from pyomo.core.base.objective import ObjectiveData, ScalarObjective from pyomo.core.base.var import Var from pyomo.gdp import Disjunct -from pyomo.core.base.expression import ExpressionData, ScalarExpression import logging from pyomo.common.errors import InfeasibleConstraintException, PyomoException from pyomo.common.config import ( @@ -340,7 +341,7 @@ def _prop_bnds_leaf_to_root_NamedExpression(visitor, node, expr): Parameters ---------- visitor: _FBBTVisitorLeafToRoot - node: pyomo.core.base.expression.ExpressionData + node: pyomo.core.base.expression.NamedExpressionData expr: NamedExpressionData arg """ bnds_dict = visitor.bnds_dict @@ -368,6 +369,8 @@ def _prop_bnds_leaf_to_root_NamedExpression(visitor, node, expr): numeric_expr.AbsExpression: _prop_bnds_leaf_to_root_abs, ExpressionData: _prop_bnds_leaf_to_root_NamedExpression, ScalarExpression: _prop_bnds_leaf_to_root_NamedExpression, + ObjectiveData: _prop_bnds_leaf_to_root_NamedExpression, + ScalarObjective: _prop_bnds_leaf_to_root_NamedExpression, }, ) @@ -904,7 +907,7 @@ def _prop_bnds_root_to_leaf_NamedExpression(node, bnds_dict, feasibility_tol): Parameters ---------- - node: pyomo.core.base.expression.ExpressionData + node: pyomo.core.base.expression.NamedExpressionData bnds_dict: ComponentMap feasibility_tol: float If the bounds computed on the body of a constraint violate the bounds of the constraint by more than @@ -947,6 +950,8 @@ def _prop_bnds_root_to_leaf_NamedExpression(node, bnds_dict, feasibility_tol): _prop_bnds_root_to_leaf_map[ExpressionData] = _prop_bnds_root_to_leaf_NamedExpression _prop_bnds_root_to_leaf_map[ScalarExpression] = _prop_bnds_root_to_leaf_NamedExpression +_prop_bnds_root_to_leaf_map[ObjectiveData] = _prop_bnds_root_to_leaf_NamedExpression +_prop_bnds_root_to_leaf_map[ScalarObjective] = _prop_bnds_root_to_leaf_NamedExpression def _check_and_reset_bounds(var, lb, ub): From e35d537d30e6e28d2c54737408adcf24d7ae361d Mon Sep 17 00:00:00 2001 From: John Siirola Date: Thu, 18 Apr 2024 09:54:18 -0600 Subject: [PATCH 75/83] Fix docstring --- pyomo/core/base/constraint.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyomo/core/base/constraint.py b/pyomo/core/base/constraint.py index 3a71758d55d..eb4af76fdc1 100644 --- a/pyomo/core/base/constraint.py +++ b/pyomo/core/base/constraint.py @@ -127,7 +127,7 @@ def C_rule(model, i, j): class ConstraintData(ActiveComponentData): """ - This class defines the data for a single general constraint. + This class defines the data for a single algebraic constraint. Constructor arguments: component The Constraint object that owns this data. From ebe0159071ef2a60a6e71dd3131913907e5aa64b Mon Sep 17 00:00:00 2001 From: robbybp Date: Fri, 19 Apr 2024 23:15:33 -0600 Subject: [PATCH 76/83] start adding an inventory of code to readme --- pyomo/contrib/pynumero/README.md | 31 +++++++++++++++++++++++++++++++ 1 file changed, 31 insertions(+) diff --git a/pyomo/contrib/pynumero/README.md b/pyomo/contrib/pynumero/README.md index 0d165dbc39c..d4b6344ec76 100644 --- a/pyomo/contrib/pynumero/README.md +++ b/pyomo/contrib/pynumero/README.md @@ -71,3 +71,34 @@ Prerequisites - cmake - a C/C++ compiler - MA57 library or COIN-HSL Full + +Code organization +================= + +PyNumero was initially designed around three core components: linear solver +interfaces, an interface for function and derivative callbacks, and block +vector and matrix classes. Since then, it has incorporated additional +functionality in an ad-hoc manner. The following is a rough overview of +PyNumero, by directory: + +`linalg` +-------- + +Python interfaces to linear solvers. This is core functionality. + +`interfaces` +------------ + +- Classes that define and implement an API for function and derivative callbacks +required by nonlinear optimization solvers, e.g. `nlp.py` and `pyomo_nlp.py` +- Various wrappers around these NLP classes to support "hybrid" implementations, +e.g. `PyomoNLPWithGreyBoxBlocks` +- The `ExternalGreyBoxBlock` Pyomo modeling component and +`ExternalGreyBoxModel` API +- The `ExternalPyomoModel` implementation of `ExternalGreyBoxModel`, which allows +definition of an external grey box via an implicit function +- The `CyIpoptNLP` class, which wraps an object implementing the NLP API in +the interface required by CyIpopt + +`src` +----- From d4dcb0e81bbc20dc6597fc76b1400b81c02cd100 Mon Sep 17 00:00:00 2001 From: robbybp Date: Fri, 19 Apr 2024 23:16:14 -0600 Subject: [PATCH 77/83] add a note about backward compatibility to pynumero doc --- .../pynumero/backward_compatibility.rst | 14 ++++++++++++++ .../contributed_packages/pynumero/index.rst | 1 + 2 files changed, 15 insertions(+) create mode 100644 doc/OnlineDocs/contributed_packages/pynumero/backward_compatibility.rst diff --git a/doc/OnlineDocs/contributed_packages/pynumero/backward_compatibility.rst b/doc/OnlineDocs/contributed_packages/pynumero/backward_compatibility.rst new file mode 100644 index 00000000000..036a00bee62 --- /dev/null +++ b/doc/OnlineDocs/contributed_packages/pynumero/backward_compatibility.rst @@ -0,0 +1,14 @@ +Backward Compatibility +====================== + +While PyNumero is a third-party contribution to Pyomo, we intend to maintain +the stability of its core functionality. The core functionality of PyNumero +consists of: + +1. The ``NLP`` API and ``PyomoNLP`` implementation of this API +2. HSL and MUMPS linear solver interfaces +3. ``BlockVector`` and ``BlockMatrix`` classes +4. CyIpopt and SciPy solver interfaces + +Other parts of PyNumero, such as ``ExternalGreyBoxBlock`` and +``ImplicitFunctionSolver``, are experimental and subject to change without notice. diff --git a/doc/OnlineDocs/contributed_packages/pynumero/index.rst b/doc/OnlineDocs/contributed_packages/pynumero/index.rst index 6ff8b29f812..711bb83eb3b 100644 --- a/doc/OnlineDocs/contributed_packages/pynumero/index.rst +++ b/doc/OnlineDocs/contributed_packages/pynumero/index.rst @@ -13,6 +13,7 @@ PyNumero. For more details, see the API documentation (:ref:`pynumero_api`). installation.rst tutorial.rst api.rst + backward_compatibility.rst Developers From 102223f541f82b38085c15489d2884744dfbb8f8 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Mon, 22 Apr 2024 15:25:46 -0600 Subject: [PATCH 78/83] NFC: clarify NamedExpressionData docstring --- pyomo/core/base/expression.py | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/pyomo/core/base/expression.py b/pyomo/core/base/expression.py index 5638e48ea8b..013c388e6e5 100644 --- a/pyomo/core/base/expression.py +++ b/pyomo/core/base/expression.py @@ -37,11 +37,14 @@ class NamedExpressionData(numeric_expr.NumericValue): - """ - An object that defines a named expression. + """An object that defines a generic "named expression". + + This is the base class for both :py:class:`ExpressionData` and + :py:class:`ObjectiveData`. Public Class Attributes expr The expression owned by this data. + """ # Note: derived classes are expected to declare the _args_ slot From f1d480fe970472acc1919f4b32c8f9808bc2a179 Mon Sep 17 00:00:00 2001 From: Emma Johnson Date: Wed, 24 Apr 2024 09:55:31 -0600 Subject: [PATCH 79/83] Fixing a bug where a division by 0 wasn't trapped and propogated as an invalid number --- pyomo/repn/linear.py | 2 +- pyomo/repn/tests/test_linear.py | 16 ++++++++++++++++ 2 files changed, 17 insertions(+), 1 deletion(-) diff --git a/pyomo/repn/linear.py b/pyomo/repn/linear.py index ba08c7ef245..6d084067511 100644 --- a/pyomo/repn/linear.py +++ b/pyomo/repn/linear.py @@ -292,7 +292,7 @@ def _handle_division_constant_constant(visitor, node, arg1, arg2): def _handle_division_ANY_constant(visitor, node, arg1, arg2): - arg1[1].multiplier /= arg2[1] + arg1[1].multiplier = apply_node_operation(node, (arg1[1].multiplier, arg2[1])) return arg1 diff --git a/pyomo/repn/tests/test_linear.py b/pyomo/repn/tests/test_linear.py index 0fd428fd8ee..861fecc7888 100644 --- a/pyomo/repn/tests/test_linear.py +++ b/pyomo/repn/tests/test_linear.py @@ -1436,6 +1436,22 @@ def test_errors_propagate_nan(self): m.z = Var() m.y.fix(1) + expr = (m.x + 1) / m.p + cfg = VisitorConfig() + with LoggingIntercept() as LOG: + repn = LinearRepnVisitor(*cfg).walk_expression(expr) + self.assertEqual( + LOG.getvalue(), + "Exception encountered evaluating expression 'div(1, 0)'\n" + "\tmessage: division by zero\n" + "\texpression: (x + 1)/p\n", + ) + self.assertEqual(repn.multiplier, 1) + self.assertEqual(str(repn.constant), 'InvalidNumber(nan)') + self.assertEqual(len(repn.linear), 1) + self.assertEqual(str(repn.linear[id(m.x)]), 'InvalidNumber(nan)') + self.assertEqual(repn.nonlinear, None) + expr = m.y + m.x + m.z + ((3 * m.x) / m.p) / m.y cfg = VisitorConfig() with LoggingIntercept() as LOG: From ea9d226f368959e3e028a4bd9a4a7bb77ea29938 Mon Sep 17 00:00:00 2001 From: John Siirola Date: Wed, 24 Apr 2024 22:08:44 -0600 Subject: [PATCH 80/83] Skip black 24.4.1 due to a bug in the parser --- .github/workflows/test_branches.yml | 3 ++- .github/workflows/test_pr_and_main.yml | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/.github/workflows/test_branches.yml b/.github/workflows/test_branches.yml index 1885f6a00e2..75db5d66431 100644 --- a/.github/workflows/test_branches.yml +++ b/.github/workflows/test_branches.yml @@ -40,7 +40,8 @@ jobs: python-version: '3.10' - name: Black Formatting Check run: | - pip install black + # Note v24.4.1 fails due to a bug in the parser + pip install 'black!=24.4.1' black . -S -C --check --diff --exclude examples/pyomobook/python-ch/BadIndent.py - name: Spell Check uses: crate-ci/typos@master diff --git a/.github/workflows/test_pr_and_main.yml b/.github/workflows/test_pr_and_main.yml index 619a5e695e2..eb059a7ef82 100644 --- a/.github/workflows/test_pr_and_main.yml +++ b/.github/workflows/test_pr_and_main.yml @@ -43,7 +43,8 @@ jobs: python-version: '3.10' - name: Black Formatting Check run: | - pip install black + # Note v24.4.1 fails due to a bug in the parser + pip install 'black!=24.4.1' black . -S -C --check --diff --exclude examples/pyomobook/python-ch/BadIndent.py - name: Spell Check uses: crate-ci/typos@master From 98ee3ec8ad70b49f25a8aade1453c1d3be58ac8a Mon Sep 17 00:00:00 2001 From: robbybp Date: Wed, 24 Apr 2024 22:16:20 -0600 Subject: [PATCH 81/83] add more description to readme --- pyomo/contrib/pynumero/README.md | 43 ++++++++++++++++++++++++++++++-- 1 file changed, 41 insertions(+), 2 deletions(-) diff --git a/pyomo/contrib/pynumero/README.md b/pyomo/contrib/pynumero/README.md index d4b6344ec76..d68c055e97c 100644 --- a/pyomo/contrib/pynumero/README.md +++ b/pyomo/contrib/pynumero/README.md @@ -78,8 +78,13 @@ Code organization PyNumero was initially designed around three core components: linear solver interfaces, an interface for function and derivative callbacks, and block vector and matrix classes. Since then, it has incorporated additional -functionality in an ad-hoc manner. The following is a rough overview of -PyNumero, by directory: +functionality in an ad-hoc manner. The original "core functionality" of +PyNumero, as well as the solver interfaces accessible through +`SolverFactory`, should be considered stable and will only change after +appropriate deprecation warnings. Other functionality should be considered +experimental and subject to change without warning. + +The following is a rough overview of PyNumero, by directory: `linalg` -------- @@ -100,5 +105,39 @@ definition of an external grey box via an implicit function - The `CyIpoptNLP` class, which wraps an object implementing the NLP API in the interface required by CyIpopt +Of the above, only `PyomoNLP` and the `NLP` base class should be considered core +functionality. + `src` ----- + +C++ interfaces to ASL, MA27, and MA57. The ASL and MA27 interfaces are +core functionality. + +`sparse` +-------- + +Block vector and block matrix classes, including MPI variations. +These are core functionality. + +`algorithms` +------------ + +Originally intended to hold various useful algorithms implemented +on NLP objects rather than Pyomo models. Any files added here should +be considered experimental. + +`algorithms/solvers` +-------------------- + +Interfaces to Python solvers using the NLP API defined in `interfaces`. +Only the solvers accessible through `SolverFactory`, e.g. `PyomoCyIpoptSolver` +and `PyomoFsolveSolver`, should be considered core functionality. + +`examples` +---------- + +The examples demonstrated in `nlp_interface.py`, `nlp_interface_2.py1`, +`feasibility.py`, `mumps_example.py`, `sensitivity.py`, `sqp.py`, +`parallel_matvec.py`, and `parallel_vector_ops.py` are stable. All other +examples should be considered experimental. From 5689e7406574d5baa8d80c38f91264f7d9fc59ed Mon Sep 17 00:00:00 2001 From: Robert Parker Date: Thu, 25 Apr 2024 09:33:06 -0600 Subject: [PATCH 82/83] add note that location of pyomo solvers is subject to change --- pyomo/contrib/pynumero/README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/pyomo/contrib/pynumero/README.md b/pyomo/contrib/pynumero/README.md index d68c055e97c..f881e400d51 100644 --- a/pyomo/contrib/pynumero/README.md +++ b/pyomo/contrib/pynumero/README.md @@ -133,6 +133,8 @@ be considered experimental. Interfaces to Python solvers using the NLP API defined in `interfaces`. Only the solvers accessible through `SolverFactory`, e.g. `PyomoCyIpoptSolver` and `PyomoFsolveSolver`, should be considered core functionality. +The supported way to access these solvers is via `SolverFactory`. *The locations +of the underlying solver objects are subject to change without warning.* `examples` ---------- From a0bc0891f900993692c65c88c2c0e9aacc435d88 Mon Sep 17 00:00:00 2001 From: Miranda Mundt <55767766+mrmundt@users.noreply.github.com> Date: Thu, 25 Apr 2024 11:30:23 -0600 Subject: [PATCH 83/83] Incorporate suggestion on wording Co-authored-by: Bethany Nicholson --- doc/OnlineDocs/contribution_guide.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/OnlineDocs/contribution_guide.rst b/doc/OnlineDocs/contribution_guide.rst index 6054a8d2ba9..b98dcc3d014 100644 --- a/doc/OnlineDocs/contribution_guide.rst +++ b/doc/OnlineDocs/contribution_guide.rst @@ -93,7 +93,7 @@ active development may be marked 'stale' and closed. .. note:: Draft and WIP Pull Requests will **NOT** trigger tests. This is an effort to - keep our backlog as available as possible. Please make use of the provided + reduce our CI backlog. Please make use of the provided branch test suite for evaluating / testing draft functionality. Python Version Support