Note
Go to the end to download the full example code.
Branch-and-check MethodΒΆ
Prepare the problem for Benders decomposition.
from benderslib import ClassicalBenders, AnnotatedBenders
from benderslib.solvers import Gurobi
from benderslib.utils import draw_curve
from gurobipy import Model, GRB
def make_original_problem():
model = Model("Original")
n_vars = 20
y = model.addVars(n_vars, name="y", lb=1, ub=40, vtype=GRB.INTEGER)
z = model.addVars(n_vars, name="z", lb=1, ub=40, vtype=GRB.CONTINUOUS)
model.addConstr(y.sum() + z.sum() <= 50 * n_vars, "main_constr_yz")
model.addConstrs((2 * y[i] <= 2 * (i + 1) for i in range(n_vars)), name="constr_y")
model.addConstrs((2 * y[i] + z[i] >= i for i in range(n_vars)), name="constr_yz")
model.addConstrs((3 * z[i] <= 15 for i in range(n_vars)), name="constr_z")
model.setObjective(2 * y.sum() + 3 * z.sum(), sense=GRB.MINIMIZE)
model.Params.OutputFlag = 0
model.Params.LogToConsole = 0
model.update()
complicating_vars = [v.VarName for v in y.values()]
return model, complicating_vars
Solve the problem using Branch-and-check method:
model, complicating_vars = make_original_problem()
BD = AnnotatedBenders(
model,
solver=Gurobi,
complicating_vars=complicating_vars,
benders=ClassicalBenders
)
BD.params.tol_rel = 0.05
BD.bnc_solve()
draw_curve(BD.result)
See also
A brief introduction to Branch-and-check Method.
Its classical implementation counterpart is Annotated Benders Decomposition. The acceleration is remarkable!!