mirror of
https://github.com/ANL-CEEESA/MIPLearn.git
synced 2025-12-06 01:18:52 -06:00
Move instance fixtures into the main source; remove duplication
This commit is contained in:
@@ -289,35 +289,3 @@ class KnapsackInstance(Instance):
|
||||
self.weights[item],
|
||||
self.prices[item],
|
||||
]
|
||||
|
||||
|
||||
class GurobiKnapsackInstance(KnapsackInstance):
|
||||
"""
|
||||
Simpler (one-dimensional) knapsack instance, implemented directly in Gurobi
|
||||
instead of Pyomo, used for testing.
|
||||
"""
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
weights: List[float],
|
||||
prices: List[float],
|
||||
capacity: float,
|
||||
) -> None:
|
||||
super().__init__(weights, prices, capacity)
|
||||
|
||||
@overrides
|
||||
def to_model(self) -> Any:
|
||||
import gurobipy as gp
|
||||
from gurobipy import GRB
|
||||
|
||||
model = gp.Model("Knapsack")
|
||||
n = len(self.weights)
|
||||
x = model.addVars(n, vtype=GRB.BINARY, name="x")
|
||||
model.addConstr(
|
||||
gp.quicksum(x[i] * self.weights[i] for i in range(n)) <= self.capacity,
|
||||
"eq_capacity",
|
||||
)
|
||||
model.setObjective(
|
||||
gp.quicksum(x[i] * self.prices[i] for i in range(n)), GRB.MAXIMIZE
|
||||
)
|
||||
return model
|
||||
|
||||
@@ -19,6 +19,7 @@ from miplearn.solvers.internal import (
|
||||
LazyCallback,
|
||||
MIPSolveStats,
|
||||
)
|
||||
from miplearn.solvers.pyomo.base import PyomoTestInstanceKnapsack
|
||||
from miplearn.types import (
|
||||
SolverParams,
|
||||
UserCutCallback,
|
||||
@@ -442,3 +443,77 @@ class GurobiSolver(InternalSolver):
|
||||
params=self.params,
|
||||
lazy_cb_frequency=self.lazy_cb_frequency,
|
||||
)
|
||||
|
||||
@overrides
|
||||
def build_test_instance_infeasible(self) -> Instance:
|
||||
return GurobiTestInstanceInfeasible()
|
||||
|
||||
@overrides
|
||||
def build_test_instance_redundancy(self) -> Instance:
|
||||
return GurobiTestInstanceRedundancy()
|
||||
|
||||
@overrides
|
||||
def build_test_instance_knapsack(self) -> Instance:
|
||||
return GurobiTestInstanceKnapsack(
|
||||
weights=[23.0, 26.0, 20.0, 18.0],
|
||||
prices=[505.0, 352.0, 458.0, 220.0],
|
||||
capacity=67.0,
|
||||
)
|
||||
|
||||
|
||||
class GurobiTestInstanceInfeasible(Instance):
|
||||
@overrides
|
||||
def to_model(self) -> Any:
|
||||
import gurobipy as gp
|
||||
from gurobipy import GRB
|
||||
|
||||
model = gp.Model()
|
||||
x = model.addVars(1, vtype=GRB.BINARY, name="x")
|
||||
model.addConstr(x[0] >= 2)
|
||||
model.setObjective(x[0])
|
||||
return model
|
||||
|
||||
|
||||
class GurobiTestInstanceRedundancy(Instance):
|
||||
def to_model(self) -> Any:
|
||||
import gurobipy as gp
|
||||
from gurobipy import GRB
|
||||
|
||||
model = gp.Model()
|
||||
x = model.addVars(2, vtype=GRB.BINARY, name="x")
|
||||
model.addConstr(x[0] + x[1] <= 1)
|
||||
model.addConstr(x[0] + x[1] <= 2)
|
||||
model.setObjective(x[0] + x[1], GRB.MAXIMIZE)
|
||||
return model
|
||||
|
||||
|
||||
class GurobiTestInstanceKnapsack(PyomoTestInstanceKnapsack):
|
||||
"""
|
||||
Simpler (one-dimensional) knapsack instance, implemented directly in Gurobi
|
||||
instead of Pyomo, used for testing.
|
||||
"""
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
weights: List[float],
|
||||
prices: List[float],
|
||||
capacity: float,
|
||||
) -> None:
|
||||
super().__init__(weights, prices, capacity)
|
||||
|
||||
@overrides
|
||||
def to_model(self) -> Any:
|
||||
import gurobipy as gp
|
||||
from gurobipy import GRB
|
||||
|
||||
model = gp.Model("Knapsack")
|
||||
n = len(self.weights)
|
||||
x = model.addVars(n, vtype=GRB.BINARY, name="x")
|
||||
model.addConstr(
|
||||
gp.quicksum(x[i] * self.weights[i] for i in range(n)) <= self.capacity,
|
||||
"eq_capacity",
|
||||
)
|
||||
model.setObjective(
|
||||
gp.quicksum(x[i] * self.prices[i] for i in range(n)), GRB.MAXIMIZE
|
||||
)
|
||||
return model
|
||||
|
||||
@@ -292,3 +292,15 @@ class InternalSolver(ABC):
|
||||
completely unitialized.
|
||||
"""
|
||||
pass
|
||||
|
||||
@abstractmethod
|
||||
def build_test_instance_infeasible(self) -> Instance:
|
||||
pass
|
||||
|
||||
@abstractmethod
|
||||
def build_test_instance_redundancy(self) -> Instance:
|
||||
pass
|
||||
|
||||
@abstractmethod
|
||||
def build_test_instance_knapsack(self) -> Instance:
|
||||
pass
|
||||
|
||||
@@ -29,7 +29,9 @@ from miplearn.types import (
|
||||
UserCutCallback,
|
||||
Solution,
|
||||
VariableName,
|
||||
Category,
|
||||
)
|
||||
import numpy as np
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
@@ -338,3 +340,88 @@ class BasePyomoSolver(InternalSolver):
|
||||
@overrides
|
||||
def get_sense(self) -> str:
|
||||
return self._obj_sense
|
||||
|
||||
@overrides
|
||||
def build_test_instance_infeasible(self) -> Instance:
|
||||
return PyomoTestInstanceInfeasible()
|
||||
|
||||
@overrides
|
||||
def build_test_instance_redundancy(self) -> Instance:
|
||||
return PyomoTestInstanceRedundancy()
|
||||
|
||||
@overrides
|
||||
def build_test_instance_knapsack(self) -> Instance:
|
||||
return PyomoTestInstanceKnapsack(
|
||||
weights=[23.0, 26.0, 20.0, 18.0],
|
||||
prices=[505.0, 352.0, 458.0, 220.0],
|
||||
capacity=67.0,
|
||||
)
|
||||
|
||||
|
||||
class PyomoTestInstanceInfeasible(Instance):
|
||||
@overrides
|
||||
def to_model(self) -> pe.ConcreteModel:
|
||||
model = pe.ConcreteModel()
|
||||
model.x = pe.Var([0], domain=pe.Binary)
|
||||
model.OBJ = pe.Objective(expr=model.x[0], sense=pe.maximize)
|
||||
model.eq = pe.Constraint(expr=model.x[0] >= 2)
|
||||
return model
|
||||
|
||||
|
||||
class PyomoTestInstanceRedundancy(Instance):
|
||||
def to_model(self) -> pe.ConcreteModel:
|
||||
model = pe.ConcreteModel()
|
||||
model.x = pe.Var([0, 1], domain=pe.Binary)
|
||||
model.OBJ = pe.Objective(expr=model.x[0] + model.x[1], sense=pe.maximize)
|
||||
model.eq1 = pe.Constraint(expr=model.x[0] + model.x[1] <= 1)
|
||||
model.eq2 = pe.Constraint(expr=model.x[0] + model.x[1] <= 2)
|
||||
return model
|
||||
|
||||
|
||||
class PyomoTestInstanceKnapsack(Instance):
|
||||
"""
|
||||
Simpler (one-dimensional) Knapsack Problem, used for testing.
|
||||
"""
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
weights: List[float],
|
||||
prices: List[float],
|
||||
capacity: float,
|
||||
) -> None:
|
||||
super().__init__()
|
||||
self.weights = weights
|
||||
self.prices = prices
|
||||
self.capacity = capacity
|
||||
self.varname_to_item: Dict[VariableName, int] = {
|
||||
f"x[{i}]": i for i in range(len(self.weights))
|
||||
}
|
||||
|
||||
@overrides
|
||||
def to_model(self) -> pe.ConcreteModel:
|
||||
model = pe.ConcreteModel()
|
||||
items = range(len(self.weights))
|
||||
model.x = pe.Var(items, domain=pe.Binary)
|
||||
model.OBJ = pe.Objective(
|
||||
expr=sum(model.x[v] * self.prices[v] for v in items),
|
||||
sense=pe.maximize,
|
||||
)
|
||||
model.eq_capacity = pe.Constraint(
|
||||
expr=sum(model.x[v] * self.weights[v] for v in items) <= self.capacity
|
||||
)
|
||||
return model
|
||||
|
||||
@overrides
|
||||
def get_instance_features(self) -> List[float]:
|
||||
return [
|
||||
self.capacity,
|
||||
np.average(self.weights),
|
||||
]
|
||||
|
||||
@overrides
|
||||
def get_variable_features(self, var_name: VariableName) -> List[Category]:
|
||||
item = self.varname_to_item[var_name]
|
||||
return [
|
||||
self.weights[item],
|
||||
self.prices[item],
|
||||
]
|
||||
|
||||
@@ -14,7 +14,6 @@ from miplearn.features import TrainingSample, InstanceFeatures, Features
|
||||
from miplearn.instance.base import Instance
|
||||
from miplearn.solvers.learning import LearningSolver
|
||||
from miplearn.solvers.pyomo.gurobi import GurobiPyomoSolver
|
||||
from tests.fixtures.knapsack import get_knapsack_instance
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
@@ -252,7 +251,7 @@ def test_sample_evaluate(instance: Instance, sample: TrainingSample) -> None:
|
||||
|
||||
def test_usage() -> None:
|
||||
solver = LearningSolver(components=[ObjectiveValueComponent()])
|
||||
instance = get_knapsack_instance(GurobiPyomoSolver())
|
||||
instance = GurobiPyomoSolver().build_test_instance_knapsack()
|
||||
solver.solve(instance)
|
||||
solver.fit([instance])
|
||||
stats = solver.solve(instance)
|
||||
|
||||
3
tests/fixtures/__init__.py
vendored
3
tests/fixtures/__init__.py
vendored
@@ -1,3 +0,0 @@
|
||||
# MIPLearn: Extensible Framework for Learning-Enhanced Mixed-Integer Optimization
|
||||
# Copyright (C) 2020-2021, UChicago Argonne, LLC. All rights reserved.
|
||||
# Released under the modified BSD license. See COPYING.md for more details.
|
||||
44
tests/fixtures/infeasible.py
vendored
44
tests/fixtures/infeasible.py
vendored
@@ -1,44 +0,0 @@
|
||||
# MIPLearn: Extensible Framework for Learning-Enhanced Mixed-Integer Optimization
|
||||
# Copyright (C) 2020-2021, UChicago Argonne, LLC. All rights reserved.
|
||||
# Released under the modified BSD license. See COPYING.md for more details.
|
||||
|
||||
from typing import Any
|
||||
|
||||
from overrides import overrides
|
||||
from pyomo import environ as pe
|
||||
|
||||
from miplearn.instance.base import Instance
|
||||
from miplearn.solvers.gurobi import GurobiSolver
|
||||
from miplearn.solvers.pyomo.base import BasePyomoSolver
|
||||
from tests.solvers import _is_subclass_or_instance
|
||||
|
||||
|
||||
class InfeasiblePyomoInstance(Instance):
|
||||
@overrides
|
||||
def to_model(self) -> pe.ConcreteModel:
|
||||
model = pe.ConcreteModel()
|
||||
model.x = pe.Var([0], domain=pe.Binary)
|
||||
model.OBJ = pe.Objective(expr=model.x[0], sense=pe.maximize)
|
||||
model.eq = pe.Constraint(expr=model.x[0] >= 2)
|
||||
return model
|
||||
|
||||
|
||||
class InfeasibleGurobiInstance(Instance):
|
||||
@overrides
|
||||
def to_model(self) -> Any:
|
||||
import gurobipy as gp
|
||||
from gurobipy import GRB
|
||||
|
||||
model = gp.Model()
|
||||
x = model.addVars(1, vtype=GRB.BINARY, name="x")
|
||||
model.addConstr(x[0] >= 2)
|
||||
model.setObjective(x[0])
|
||||
return model
|
||||
|
||||
|
||||
def get_infeasible_instance(solver: Any) -> Instance:
|
||||
if _is_subclass_or_instance(solver, BasePyomoSolver):
|
||||
return InfeasiblePyomoInstance()
|
||||
if _is_subclass_or_instance(solver, GurobiSolver):
|
||||
return InfeasibleGurobiInstance()
|
||||
assert False
|
||||
50
tests/fixtures/knapsack.py
vendored
50
tests/fixtures/knapsack.py
vendored
@@ -1,50 +0,0 @@
|
||||
# MIPLearn: Extensible Framework for Learning-Enhanced Mixed-Integer Optimization
|
||||
# Copyright (C) 2020-2021, UChicago Argonne, LLC. All rights reserved.
|
||||
# Released under the modified BSD license. See COPYING.md for more details.
|
||||
|
||||
from typing import List, Any, Tuple
|
||||
|
||||
from miplearn.instance.base import Instance
|
||||
from miplearn.problems.knapsack import KnapsackInstance, GurobiKnapsackInstance
|
||||
from miplearn.solvers.gurobi import GurobiSolver
|
||||
from miplearn.solvers.internal import InternalSolver
|
||||
from miplearn.solvers.learning import LearningSolver
|
||||
from miplearn.solvers.pyomo.base import BasePyomoSolver
|
||||
from tests.solvers import _is_subclass_or_instance
|
||||
|
||||
|
||||
def get_test_pyomo_instances() -> Tuple[List[Instance], List[Any]]:
|
||||
instances: List[Instance] = [
|
||||
KnapsackInstance(
|
||||
weights=[23.0, 26.0, 20.0, 18.0],
|
||||
prices=[505.0, 352.0, 458.0, 220.0],
|
||||
capacity=67.0,
|
||||
),
|
||||
KnapsackInstance(
|
||||
weights=[25.0, 30.0, 22.0, 18.0],
|
||||
prices=[500.0, 365.0, 420.0, 150.0],
|
||||
capacity=70.0,
|
||||
),
|
||||
]
|
||||
models = [instance.to_model() for instance in instances]
|
||||
solver = LearningSolver()
|
||||
for i in range(len(instances)):
|
||||
solver.solve(instances[i], models[i])
|
||||
return instances, models
|
||||
|
||||
|
||||
def get_knapsack_instance(solver: InternalSolver) -> Instance:
|
||||
if _is_subclass_or_instance(solver, BasePyomoSolver):
|
||||
return KnapsackInstance(
|
||||
weights=[23.0, 26.0, 20.0, 18.0],
|
||||
prices=[505.0, 352.0, 458.0, 220.0],
|
||||
capacity=67.0,
|
||||
)
|
||||
elif _is_subclass_or_instance(solver, GurobiSolver):
|
||||
return GurobiKnapsackInstance(
|
||||
weights=[23.0, 26.0, 20.0, 18.0],
|
||||
prices=[505.0, 352.0, 458.0, 220.0],
|
||||
capacity=67.0,
|
||||
)
|
||||
else:
|
||||
assert False
|
||||
42
tests/fixtures/redundant.py
vendored
42
tests/fixtures/redundant.py
vendored
@@ -1,42 +0,0 @@
|
||||
# MIPLearn: Extensible Framework for Learning-Enhanced Mixed-Integer Optimization
|
||||
# Copyright (C) 2020-2021, UChicago Argonne, LLC. All rights reserved.
|
||||
# Released under the modified BSD license. See COPYING.md for more details.
|
||||
from typing import Any
|
||||
|
||||
import pyomo.environ as pe
|
||||
|
||||
from miplearn.instance.base import Instance
|
||||
from miplearn.solvers.gurobi import GurobiSolver
|
||||
from miplearn.solvers.pyomo.base import BasePyomoSolver
|
||||
from tests.solvers import _is_subclass_or_instance
|
||||
|
||||
|
||||
class PyomoInstanceWithRedundancy(Instance):
|
||||
def to_model(self) -> pe.ConcreteModel:
|
||||
model = pe.ConcreteModel()
|
||||
model.x = pe.Var([0, 1], domain=pe.Binary)
|
||||
model.OBJ = pe.Objective(expr=model.x[0] + model.x[1], sense=pe.maximize)
|
||||
model.eq1 = pe.Constraint(expr=model.x[0] + model.x[1] <= 1)
|
||||
model.eq2 = pe.Constraint(expr=model.x[0] + model.x[1] <= 2)
|
||||
return model
|
||||
|
||||
|
||||
class GurobiInstanceWithRedundancy(Instance):
|
||||
def to_model(self) -> Any:
|
||||
import gurobipy as gp
|
||||
from gurobipy import GRB
|
||||
|
||||
model = gp.Model()
|
||||
x = model.addVars(2, vtype=GRB.BINARY, name="x")
|
||||
model.addConstr(x[0] + x[1] <= 1)
|
||||
model.addConstr(x[0] + x[1] <= 2)
|
||||
model.setObjective(x[0] + x[1], GRB.MAXIMIZE)
|
||||
return model
|
||||
|
||||
|
||||
def get_instance_with_redundancy(solver: Any) -> Instance:
|
||||
if _is_subclass_or_instance(solver, BasePyomoSolver):
|
||||
return PyomoInstanceWithRedundancy()
|
||||
if _is_subclass_or_instance(solver, GurobiSolver):
|
||||
return GurobiInstanceWithRedundancy()
|
||||
assert False
|
||||
@@ -5,11 +5,10 @@ import tempfile
|
||||
|
||||
from miplearn.instance.picklegz import write_pickle_gz, PickleGzInstance
|
||||
from miplearn.solvers.gurobi import GurobiSolver
|
||||
from tests.fixtures.knapsack import get_knapsack_instance
|
||||
|
||||
|
||||
def test_usage() -> None:
|
||||
original = get_knapsack_instance(GurobiSolver())
|
||||
original = GurobiSolver().build_test_instance_knapsack()
|
||||
file = tempfile.NamedTemporaryFile()
|
||||
write_pickle_gz(original, file.name)
|
||||
pickled = PickleGzInstance(file.name)
|
||||
|
||||
@@ -1,33 +0,0 @@
|
||||
# MIPLearn: Extensible Framework for Learning-Enhanced Mixed-Integer Optimization
|
||||
# Copyright (C) 2020-2021, UChicago Argonne, LLC. All rights reserved.
|
||||
# Released under the modified BSD license. See COPYING.md for more details.
|
||||
|
||||
from inspect import isclass
|
||||
from typing import Any
|
||||
|
||||
from miplearn.instance.base import Instance
|
||||
from miplearn.problems.knapsack import KnapsackInstance, GurobiKnapsackInstance
|
||||
from miplearn.solvers.gurobi import GurobiSolver
|
||||
from miplearn.solvers.pyomo.base import BasePyomoSolver
|
||||
|
||||
|
||||
def _is_subclass_or_instance(obj: Any, parent_class: Any) -> bool:
|
||||
return isinstance(obj, parent_class) or (
|
||||
isclass(obj) and issubclass(obj, parent_class)
|
||||
)
|
||||
|
||||
|
||||
def _get_knapsack_instance(solver: Any) -> Instance:
|
||||
if _is_subclass_or_instance(solver, BasePyomoSolver):
|
||||
return KnapsackInstance(
|
||||
weights=[23.0, 26.0, 20.0, 18.0],
|
||||
prices=[505.0, 352.0, 458.0, 220.0],
|
||||
capacity=67.0,
|
||||
)
|
||||
if _is_subclass_or_instance(solver, GurobiSolver):
|
||||
return GurobiKnapsackInstance(
|
||||
weights=[23.0, 26.0, 20.0, 18.0],
|
||||
prices=[505.0, 352.0, 458.0, 220.0],
|
||||
capacity=67.0,
|
||||
)
|
||||
assert False
|
||||
|
||||
@@ -13,11 +13,9 @@ from miplearn import InternalSolver
|
||||
from miplearn.solvers import _RedirectOutput
|
||||
from miplearn.solvers.gurobi import GurobiSolver
|
||||
from miplearn.solvers.pyomo.base import BasePyomoSolver
|
||||
from . import _get_knapsack_instance
|
||||
|
||||
# noinspection PyUnresolvedReferences
|
||||
from .. import internal_solvers
|
||||
from ..fixtures.infeasible import get_infeasible_instance
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
@@ -38,7 +36,7 @@ def test_internal_solver_warm_starts(
|
||||
) -> None:
|
||||
for solver in internal_solvers:
|
||||
logger.info("Solver: %s" % solver)
|
||||
instance = _get_knapsack_instance(solver)
|
||||
instance = solver.build_test_instance_knapsack()
|
||||
model = instance.to_model()
|
||||
solver.set_instance(instance, model)
|
||||
solver.set_warm_start({"x[0]": 1.0, "x[1]": 0.0, "x[2]": 0.0, "x[3]": 1.0})
|
||||
@@ -64,7 +62,7 @@ def test_internal_solver(
|
||||
for solver in internal_solvers:
|
||||
logger.info("Solver: %s" % solver)
|
||||
|
||||
instance = _get_knapsack_instance(solver)
|
||||
instance = solver.build_test_instance_knapsack()
|
||||
model = instance.to_model()
|
||||
solver.set_instance(instance, model)
|
||||
|
||||
@@ -169,7 +167,7 @@ def test_relax(
|
||||
internal_solvers: List[InternalSolver],
|
||||
) -> None:
|
||||
for solver in internal_solvers:
|
||||
instance = _get_knapsack_instance(solver)
|
||||
instance = solver.build_test_instance_knapsack()
|
||||
solver.set_instance(instance)
|
||||
solver.relax()
|
||||
stats = solver.solve()
|
||||
@@ -181,7 +179,7 @@ def test_infeasible_instance(
|
||||
internal_solvers: List[InternalSolver],
|
||||
) -> None:
|
||||
for solver in internal_solvers:
|
||||
instance = get_infeasible_instance(solver)
|
||||
instance = solver.build_test_instance_infeasible()
|
||||
solver.set_instance(instance)
|
||||
mip_stats = solver.solve()
|
||||
|
||||
@@ -200,7 +198,7 @@ def test_iteration_cb(
|
||||
) -> None:
|
||||
for solver in internal_solvers:
|
||||
logger.info("Solver: %s" % solver)
|
||||
instance = _get_knapsack_instance(solver)
|
||||
instance = solver.build_test_instance_knapsack()
|
||||
solver.set_instance(instance)
|
||||
count = 0
|
||||
|
||||
|
||||
@@ -7,14 +7,13 @@ from typing import Any
|
||||
|
||||
from miplearn import InternalSolver
|
||||
from miplearn.solvers.gurobi import GurobiSolver
|
||||
from . import _get_knapsack_instance
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
def test_lazy_cb() -> None:
|
||||
solver = GurobiSolver()
|
||||
instance = _get_knapsack_instance(solver)
|
||||
instance = solver.build_test_instance_knapsack()
|
||||
model = instance.to_model()
|
||||
|
||||
def lazy_cb(cb_solver: InternalSolver, cb_model: Any) -> None:
|
||||
|
||||
@@ -13,7 +13,6 @@ from miplearn import Instance, InternalSolver
|
||||
from miplearn.instance.picklegz import PickleGzInstance, write_pickle_gz, read_pickle_gz
|
||||
from miplearn.solvers.gurobi import GurobiSolver
|
||||
from miplearn.solvers.learning import LearningSolver
|
||||
from . import _get_knapsack_instance
|
||||
|
||||
# noinspection PyUnresolvedReferences
|
||||
from tests import internal_solvers
|
||||
@@ -27,7 +26,7 @@ def test_learning_solver(
|
||||
for mode in ["exact", "heuristic"]:
|
||||
for internal_solver in internal_solvers:
|
||||
logger.info("Solver: %s" % internal_solver)
|
||||
instance = _get_knapsack_instance(internal_solver)
|
||||
instance = internal_solver.build_test_instance_knapsack()
|
||||
solver = LearningSolver(
|
||||
solver=internal_solver,
|
||||
mode=mode,
|
||||
@@ -71,7 +70,7 @@ def test_solve_without_lp(
|
||||
) -> None:
|
||||
for internal_solver in internal_solvers:
|
||||
logger.info("Solver: %s" % internal_solver)
|
||||
instance = _get_knapsack_instance(internal_solver)
|
||||
instance = internal_solver.build_test_instance_knapsack()
|
||||
solver = LearningSolver(
|
||||
solver=internal_solver,
|
||||
solve_lp=False,
|
||||
@@ -85,7 +84,7 @@ def test_parallel_solve(
|
||||
internal_solvers: List[InternalSolver],
|
||||
) -> None:
|
||||
for internal_solver in internal_solvers:
|
||||
instances = [_get_knapsack_instance(internal_solver) for _ in range(10)]
|
||||
instances = [internal_solver.build_test_instance_knapsack() for _ in range(10)]
|
||||
solver = LearningSolver(solver=internal_solver)
|
||||
results = solver.parallel_solve(instances, n_jobs=3)
|
||||
assert len(results) == 10
|
||||
@@ -102,7 +101,7 @@ def test_solve_fit_from_disk(
|
||||
# Create instances and pickle them
|
||||
instances: List[Instance] = []
|
||||
for k in range(3):
|
||||
instance = _get_knapsack_instance(internal_solver)
|
||||
instance = internal_solver.build_test_instance_knapsack()
|
||||
with tempfile.NamedTemporaryFile(suffix=".pkl", delete=False) as file:
|
||||
instances += [PickleGzInstance(file.name)]
|
||||
write_pickle_gz(instance, file.name)
|
||||
@@ -132,7 +131,7 @@ def test_solve_fit_from_disk(
|
||||
|
||||
def test_simulate_perfect() -> None:
|
||||
internal_solver = GurobiSolver()
|
||||
instance = _get_knapsack_instance(internal_solver)
|
||||
instance = internal_solver.build_test_instance_knapsack()
|
||||
with tempfile.NamedTemporaryFile(suffix=".pkl", delete=False) as tmp:
|
||||
write_pickle_gz(instance, tmp.name)
|
||||
solver = LearningSolver(
|
||||
|
||||
@@ -9,13 +9,12 @@ from miplearn.features import (
|
||||
ConstraintFeatures,
|
||||
)
|
||||
from miplearn.solvers.gurobi import GurobiSolver
|
||||
from tests.fixtures.knapsack import get_knapsack_instance
|
||||
|
||||
|
||||
def test_knapsack() -> None:
|
||||
for solver_factory in [GurobiSolver]:
|
||||
solver = solver_factory()
|
||||
instance = get_knapsack_instance(solver)
|
||||
instance = solver.build_test_instance_knapsack()
|
||||
model = instance.to_model()
|
||||
solver.set_instance(instance, model)
|
||||
FeaturesExtractor(solver).extract(instance)
|
||||
|
||||
Reference in New Issue
Block a user