Model#

class m4opt.milp.Model(timelimit=<Quantity 1.e+75 s>, jobs=0, memory=<Quantity inf byte>, lowercutoff=None, verbose=True)[source] [edit on github]#

Bases: Model

Convenience class to add Numpy variable arrays to a CPLEX model.

Initialize a model with default CPLEX parameters for M4OPT.

Parameters:
  • timelimit (Annotated[Quantity, PhysicalType('time')]) – Maximum solver run time. Default: run until the solver terminates naturally due to finding the optimum or proving the problem to be infeasible.

  • jobs (int) – Number of threads. If 0, then automatically configure the number of threads based on the number of CPUs present.

  • memory (Annotated[Quantity, PhysicalType('data quantity')]) – Maximum memory usage before terminating the solver.

  • lowercutoff (float | None) – Optional lower cutoff. Terminate the solver if the best bound drops below this value.

  • verbose – Display live solver progress.

Notes

  • If a time limit is provided, then set the solver emphasis to finding high-quality feasible solutions rather than proving bounds on the objective value.

  • Disable the solution pool to save memory because we only care about finding one high-quality solution and not multiple feasible solutions.

  • Enable opportunistic parallelism for faster solutions on many-core systems at the expense of results that may vary from run to run.

Attributes Summary

best_bound

Get best bound for the last solve.

Methods Summary

add_constraints_(cts[, names])

Add any number of constraints to the model.

add_indicator_constraints(indcts)

Adds a batch of indicator constraints to the model

add_indicator_constraints_(indcts)

Adds a batch of indicator constraints to the model

add_indicators(binary_vars, cts[, ...])

Add any number of indicator constraints to the model.

binary_vars([shape, lb, ub])

Create an arbitrary N-dimensional array of binary decision variables.

continuous_vars([shape, lb, ub])

Create an arbitrary N-dimensional array of continuous decision variables.

integer_vars([shape, lb, ub])

Create an arbitrary N-dimensional array of integer decision variables.

max(*args)

Builds an expression equal to the maximum value of its arguments.

min(*args)

Builds an expression equal to the minimum value of its arguments.

semicontinuous_vars([shape, lb, ub])

Create an arbitrary N-dimensional array of semicontinuous decision variables.

semiinteger_vars([shape, lb, ub])

Create an arbitrary N-dimensional array of semiinteger decision variables.

solve(**kwargs)

Starts a solve operation on the model.

to_stream(out_file)

Write the model to a stream.

Attributes Documentation

best_bound#

Get best bound for the last solve.

Notes

This is provided as a workaround for a bug in DOcplex where docplex.mp.sdetails.SolveDetails is not updated if CPLEX reaches its time limit without finding an integer solution. See IBMDecisionOptimization/docplex#17.

Methods Documentation

add_constraints_(cts, names=None)[source] [edit on github]#

Add any number of constraints to the model.

Examples

This method adds support for arrays of constraints to docplex.mp.model.Model.add_constraints_():

>>> from m4opt.milp import Model
>>> import numpy as np
>>> m = Model()
>>> x = m.continuous_vars((3, 4))
✓ adding 12 continuous variables 0:00:00
>>> xmax = np.random.normal(size=x.shape)
>>> m.add_constraints_(x >= xmax)
add_indicator_constraints(indcts)[source] [edit on github]#

Adds a batch of indicator constraints to the model

Parameters:

indcts – an iterable returning indicator constraints.

See also

indicator_constraint()

add_indicator_constraints_(indcts)[source] [edit on github]#

Adds a batch of indicator constraints to the model

Parameters:

indcts – an iterable returning indicator constraints.

See also

indicator_constraint()

add_indicators(binary_vars, cts, true_values=1, names=None)[source] [edit on github]#

Add any number of indicator constraints to the model.

Examples

This method adds support for arrays of constraints to docplex.mp.model.Model.add_indicators():

>>> from m4opt.milp import Model
>>> import numpy as np
>>> m = Model()
>>> x = m.continuous_vars((3, 4))
✓ adding 12 continuous variables 0:00:00
>>> y = m.binary_vars((3, 4))
✓ adding 12 binary variables 0:00:00
>>> xmax = np.random.normal(size=x.shape)
>>> _ = m.add_indicators(y, x >= xmax)
binary_vars(shape=(), lb=None, ub=None) [edit on github]#

Create an arbitrary N-dimensional array of binary decision variables.

Parameters:
  • shape – The desired shape of the array.

  • args – Additional arguments passed to binary_var_list(), such as lower and upper bounds.

  • kwargs – Additional arguments passed to binary_var_list(), such as lower and upper bounds.

Examples

>>> from m4opt.milp import Model
>>> import numpy as np
>>> model = Model()
>>> x = model.binary_vars()
✓ adding 1 binary variables 0:00:00
>>> y = model.binary_vars(3, lb=1, ub=1)
✓ adding 3 binary variables 0:00:00
>>> z = model.binary_vars((3, 4), lb=np.ones((3, 4)), ub=np.ones((3, 4)))
✓ adding 12 binary variables 0:00:00
>>> print(x)
x1
>>> print(y)
[x2 x3 x4]
>>> print(z)
[[x5 x6 x7 x8]
 [x9 x10 x11 x12]
 [x13 x14 x15 x16]]
continuous_vars(shape=(), lb=None, ub=None) [edit on github]#

Create an arbitrary N-dimensional array of continuous decision variables.

Parameters:
  • shape – The desired shape of the array.

  • args – Additional arguments passed to continuous_var_list(), such as lower and upper bounds.

  • kwargs – Additional arguments passed to continuous_var_list(), such as lower and upper bounds.

Examples

>>> from m4opt.milp import Model
>>> import numpy as np
>>> model = Model()
>>> x = model.continuous_vars()
✓ adding 1 continuous variables 0:00:00
>>> y = model.continuous_vars(3, lb=1, ub=1)
✓ adding 3 continuous variables 0:00:00
>>> z = model.continuous_vars((3, 4), lb=np.ones((3, 4)), ub=np.ones((3, 4)))
✓ adding 12 continuous variables 0:00:00
>>> print(x)
x1
>>> print(y)
[x2 x3 x4]
>>> print(z)
[[x5 x6 x7 x8]
 [x9 x10 x11 x12]
 [x13 x14 x15 x16]]
integer_vars(shape=(), lb=None, ub=None) [edit on github]#

Create an arbitrary N-dimensional array of integer decision variables.

Parameters:
  • shape – The desired shape of the array.

  • args – Additional arguments passed to integer_var_list(), such as lower and upper bounds.

  • kwargs – Additional arguments passed to integer_var_list(), such as lower and upper bounds.

Examples

>>> from m4opt.milp import Model
>>> import numpy as np
>>> model = Model()
>>> x = model.integer_vars()
✓ adding 1 integer variables 0:00:00
>>> y = model.integer_vars(3, lb=1, ub=1)
✓ adding 3 integer variables 0:00:00
>>> z = model.integer_vars((3, 4), lb=np.ones((3, 4)), ub=np.ones((3, 4)))
✓ adding 12 integer variables 0:00:00
>>> print(x)
x1
>>> print(y)
[x2 x3 x4]
>>> print(z)
[[x5 x6 x7 x8]
 [x9 x10 x11 x12]
 [x13 x14 x15 x16]]
max(*args)[source] [edit on github]#

Builds an expression equal to the maximum value of its arguments.

This method accepts a variable number of arguments.

Parameters:

args – A variable list of arguments, each of which is either an expression, a variable, or a container.

If passed a container or an iterator, this container or iterator must be the unique argument.

If passed one dictionary, returns the maximum of the dictionary values.

If no arguments are provided, returns negative infinity (see infinity).

Example

model.max() -> returns -model.infinity.

model.max(e) -> returns e.

model.max(e1, e2, e3) -> returns a new expression equal to the maximum of the values of e1, e2, e3.

model.max([x1,x2,x3]) where x1, x2 .. are variables or expressions -> returns the maximum of these expressions.

model.max([]) -> returns -model.infinity.

Note

Building the expression generates auxiliary variables, including binary decision variables, and this may change the nature of the problem from a LP to a MIP.

min(*args)[source] [edit on github]#

Builds an expression equal to the minimum value of its arguments.

This method accepts a variable number of arguments.

If no arguments are provided, returns positive infinity (see infinity).

Parameters:

args – A variable list of arguments, each of which is either an expression, a variable, or a container.

If passed a container or an iterator, this container or iterator must be the unique argument.

If passed one dictionary, returns the minimum of the dictionary values.

Returns:

An expression that can be used in arithmetic operators and constraints.

Example

model.min() -> returns model.infinity.

model.min(e) -> returns e.

model.min(e1, e2, e3) -> returns a new expression equal to the minimum of the values of e1, e2, e3.

model.min([x1,x2,x3]) where x1, x2 .. are variables or expressions -> returns the minimum of these expressions.

model.min([]) -> returns model.infinity.

Note

Building the expression generates auxiliary variables, including binary decision variables, and this may change the nature of the problem from a LP to a MIP.

semicontinuous_vars(shape=(), lb=None, ub=None) [edit on github]#

Create an arbitrary N-dimensional array of semicontinuous decision variables.

Parameters:

Examples

>>> from m4opt.milp import Model
>>> import numpy as np
>>> model = Model()
>>> x = model.semicontinuous_vars()
✓ adding 1 semicontinuous variables 0:00:00
>>> y = model.semicontinuous_vars(3, lb=1, ub=1)
✓ adding 3 semicontinuous variables 0:00:00
>>> z = model.semicontinuous_vars((3, 4), lb=np.ones((3, 4)), ub=np.ones((3, 4)))
✓ adding 12 semicontinuous variables 0:00:00
>>> print(x)
x1
>>> print(y)
[x2 x3 x4]
>>> print(z)
[[x5 x6 x7 x8]
 [x9 x10 x11 x12]
 [x13 x14 x15 x16]]
semiinteger_vars(shape=(), lb=None, ub=None) [edit on github]#

Create an arbitrary N-dimensional array of semiinteger decision variables.

Parameters:
  • shape – The desired shape of the array.

  • args – Additional arguments passed to semiinteger_var_list(), such as lower and upper bounds.

  • kwargs – Additional arguments passed to semiinteger_var_list(), such as lower and upper bounds.

Examples

>>> from m4opt.milp import Model
>>> import numpy as np
>>> model = Model()
>>> x = model.semiinteger_vars()
✓ adding 1 semiinteger variables 0:00:00
>>> y = model.semiinteger_vars(3, lb=1, ub=1)
✓ adding 3 semiinteger variables 0:00:00
>>> z = model.semiinteger_vars((3, 4), lb=np.ones((3, 4)), ub=np.ones((3, 4)))
✓ adding 12 semiinteger variables 0:00:00
>>> print(x)
x1
>>> print(y)
[x2 x3 x4]
>>> print(z)
[[x5 x6 x7 x8]
 [x9 x10 x11 x12]
 [x13 x14 x15 x16]]
solve(**kwargs)[source] [edit on github]#

Starts a solve operation on the model.

Parameters:
  • context (optional) – An instance of context to be used in instead of the context this model was built with.

  • cplex_parameters (optional) – A set of CPLEX parameters to use instead of the parameters defined as context.cplex_parameters. Accepts either a RootParameterGroup object (obtained by cloning the model’s parameters), or a dict of path-like names and values.

  • checker (optional) – a string which controls which type of checking is performed. Possible values are: - ‘std’ (the default) performs type checks on arguments to methods; checks that numerical arguments are numbers, but will not check for NaN or infinity. - ‘numeric’ checks that numerical arguments are valid numbers, neither NaN nor math.infinity - ‘full’ performs all possible checks, the union of ‘std’ and ‘numeric’ checks. - ‘off’ performs no checking at all. Disabling all checks might improve performance, but only when it is safe to do so.

  • log_output (optional) – if True, solver logs are output to stdout. If this is a stream, solver logs are output to that stream object. Overwrites the context.solver.log_output parameter.

  • clean_before_solve (optional) – a boolean (default is False). Solve normally picks up where the previous solve left, but if this flag is set to True, a fresh solve is started, forgetting all about previous solves..

  • parameter_sets (optional) – See create_parameter_sets()

Returns:

A docplex.mp.solution.SolveSolution object if the solve operation managed to create a feasible solution, else None. The reason why solve returned None includes not only errors, but also proper cases of infeasibilties or unboundedness. When solve returns None, use Model.solve_details to check the status of the latest solve operation: Model.solve_details always returns a docplex.mp.sdetails.SolveDetails object, whether or not a solution has been found. This object contains detailed information about the latest solve operation, such as status, elapsed time, and for MILP problems, number of nodes processed and final gap.

Return type:

SolveSolution

See also

solve_details() docplex.mp.sdetails.SolveDetails

to_stream(out_file)[source] [edit on github]#

Write the model to a stream.

The filename should end in lp, mps, sav, lp.gz, mps.gz, or sav.gz.

Parameters:

out_file (BufferedWriter)