Class ExpressionsBasedModel
- All Implemented Interfaces:
Optimisation, Optimisation.Model
Lets you construct optimisation problems by combining (mathematical) expressions in terms of variables. Each expression or variable can be a constraint and/or contribute to the objective function. An expression or variable is turned into a constraint by setting a lower and/or upper limit. Use ModelEntity.lower(Comparable), ModelEntity.upper(Comparable) or ModelEntity.level(Comparable). An expression or variable is made part of (contributing to) the objective function by setting a contribution weight. Use ModelEntity.weight(Comparable).
You may think of variables as simple (the simplest possible) expressions, and of expressions as weighted combinations of variables. They are both model entities and it is as such they can be turned into constraints and set to contribute to the objective function. Alternatively you may choose to disregard the fact that variables are model entities and simply treat them as index values. In this case everything (constraints and objective) needs to be defined using expressions.
Basic instructions:
- Create a model (new ExpressionsBasedModel()).
- Define variables using model.addVariable() and set contribution weights and lower/upper limits as needed.
- Add expressions to the model using model.addExpression() and set contribution weights and lower/upper limits as needed.
- Solve your problem using model.minimise() or model.maximise()
When using this class you do not need to worry about which solver will actually be used. The docs of the various solvers describe requirements on input formats and similar. This is handled for you and should absolutely NOT be considered here! Compared to using the various solvers directly this class actually does something for you:
- You can model your problems without worrying about specific solver requirements.
- It knows which solver to use.
- It knows how to use that solver.
- It has a presolver that tries to simplify the problem before invoking a solver (sometimes it turns out there is no need to invoke a solver at all).
- When/if needed it scales problem parameters, before creating solver specific data structures, to minimise numerical problems in the solvers.
- It's the only way to access the integer solver.
Different solvers can be used, and ojAlgo comes with a collection built in. The default built-in solvers can handle anything you can model with a couple of restrictions:
- No quadratic constraints (The plan is that future versions should not have this limitation.)
- If you use quadratic expressions make sure they're convex. This is most likely a requirement even with 3:d party solvers.
-
Nested Class Summary
Nested ClassesModifier and TypeClassDescription(package private) static final classstatic final classCounts of different kinds of model entities.static interfaceConnects solver constraints and variables back to model entities.static enumstatic classOptimisation.Solver:s that should be usabale fromExpressionsBasedModelneeds to implement a subclass of this.static enumVarious switches that can be set by solver integrations to control its own behaviour.(package private) static final classstatic class(package private) static classExpressionsBasedModel.Simplifier<ME extends ModelEntity<?>, S extends ExpressionsBasedModel.Simplifier<?,?>> static final class(package private) static class(package private) static final classNested classes/interfaces inherited from interface Optimisation
Optimisation.Constraint, Optimisation.ConstraintType, Optimisation.Model, Optimisation.Objective, Optimisation.Options, Optimisation.ProblemStructure, Optimisation.Result, Optimisation.Sense, Optimisation.Solver, Optimisation.State -
Field Summary
FieldsModifier and TypeFieldDescriptionprivate static final List<ExpressionsBasedModel.Integration<?>> private final Map<String, Expression> private final Set<Structure1D.IntIndex> private ExpressionsBasedModel.Integration<?> private booleanprivate final EnumBitSet<ExpressionsBasedModel.IntegrationProperty> private Optimisation.Resultprivate BigDecimalprivate Optimisation.Senseprivate final Set<Structure1D.IntIndex> private booleanprivate final booleanA shallow copy may share complex/large data structures with other models - typically the Map:s holding Expression parameters.private final Set<Structure1D.IntIndex> Temporary storage for some expression specific subset of variablesprivate BiConsumer<ExpressionsBasedModel, Access1D<BigDecimal>> private final ExpressionsBasedModel.VariablesCategorisationprivate static final Stringprivate static final Stringprivate static final Stringfinal Optimisation.Options(package private) static final TreeSet<ExpressionsBasedModel.Presolver> private static final String -
Constructor Summary
ConstructorsConstructorDescriptionExpressionsBasedModel(ExpressionsBasedModel modelToCopy, boolean shallow, boolean prune) ExpressionsBasedModel(Optimisation.Options optimisationOptions) -
Method Summary
Modifier and TypeMethodDescriptionaddExpression(String name) static booleanaddIntegration(Optimisation.Integration<ExpressionsBasedModel, ?> integration) Add an integration for a solver that will be used rather than the built-in solvers(package private) voidaddObjectiveConstant(BigDecimal addition) static booleanaddPresolver(ExpressionsBasedModel.Presolver presolver) (package private) voidaddReference(Structure1D.IntIndex index) voidaddSpecialOrderedSet(Collection<Variable> orderedSet, int min, int max) Calling this method will create 2 things: A simple expression meassuring the sum of the (binary) variable values (the number of binary variables that are "ON").voidaddSpecialOrderedSet(Collection<Variable> orderedSet, int type, Expression linkedTo) Creates a special ordered set (SOS) presolver instance and links that to the supplied expression.addVariable(String name) bounds()booleancheckSimilarity(Expression potential) static voidstatic voidReturns a prefiltered stream of expressions that are constraints and have not been markes as redundant.copy()copy(boolean relax) copy(boolean shallow, boolean prune) intint(package private) intderiveAdjustmentRange(Expression expression) describe()Counts variables and expressions of different categories.voiddispose()Cleanup when a model instance is no longer needed.(package private) Stream<Expression> getExpression(String name) (package private) ExpressionsBasedModel.Integration<?> (package private) Optimisation.Result(package private) BigDecimalThe default optimisation sense isOptimisation.Sense.MINIf this model was read from a file and that file format contained information about being a minimisation or maximisation model, that info is reflected here.Returns a list of the variables that are not fixed at a specific value and whos range include positive values and/or zero(package private) Set<Structure1D.IntIndex> (package private) BiConsumer<ExpressionsBasedModel, Access1D<BigDecimal>> getVariable(int index) getVariable(Structure1D.IntIndex index) getVariableValues(NumberContext validationContext) Null variable values are replaced with 0.0.intintindexOfFreeVariable(int globalIndex) intindexOfFreeVariable(Variable variable) intindexOfFreeVariable(Structure1D.IntIndex variableIndex) intindexOfIntegerVariable(int globalIndex) intindexOfIntegerVariable(Variable variable) intindexOfIntegerVariable(Structure1D.IntIndex variableIndex) intindexOfNegativeVariable(int globalIndex) intindexOfNegativeVariable(Variable variable) intindexOfNegativeVariable(Structure1D.IntIndex variableIndex) intindexOfPositiveVariable(int globalIndex) intindexOfPositiveVariable(Variable variable) intindexOfPositiveVariable(Structure1D.IntIndex variableIndex) booleanbooleanObjective or any constraint has quadratic part.booleanbooleanboolean(package private) booleanisFixed()(package private) boolean(package private) booleanisInteger(Set<Structure1D.IntIndex> variables) (package private) booleanstatic booleanisNative(ExpressionsBasedModel model) Don't you worry about this! It's for internal use.(package private) booleanisReferenced(Variable variable) (package private) boolean(package private) boolean(package private) booleanlimitObjective(BigDecimal lower, BigDecimal upper) maximise()<S extends Optimisation.Solver>
Optimisation.Resultmaximise(ExpressionsBasedModel.Integration<S> forcedIntegration) minimise()<S extends Optimisation.Solver>
Optimisation.Resultminimise(ExpressionsBasedModel.Integration<S> forcedIntegration) newExpression(String name) newVariable(String name) This is generated on demand – you should not cache this.private Optimisation.Resultoptimise(Optimisation.Sense sense, ExpressionsBasedModel.Integration<?> forcedIntegration) static ExpressionsBasedModelApart from the "native" EBM file format, currently only supports the MPS file format, but with some of the various extensions.static ExpressionsBasedModelparse(InputStream input, ExpressionsBasedModel.FileFormat format) <T extends IntermediateSolver>
Tprepare(Function<ExpressionsBasedModel, T> factory) The general recommendation is to NOT call this method directly.(package private) voidpresolve()reduce()Will try to identify constraints with equal variable sets, and check if those can be combined or not.voidrelax()voidrelax(boolean soft) voidremoveExpression(String name) static booleanremoveIntegration(ExpressionsBasedModel.Integration<?> integration) static booleanremovePresolver(ExpressionsBasedModel.Presolver presolver) static voidprivate void(package private) void(package private) voidsetIntegrationSwitch(ExpressionsBasedModel.IntegrationProperty property, boolean value) voidsetKnownSolution(Optimisation.Result knownSolution) Same assetKnownSolution(org.ojalgo.optimisation.Optimisation.Result, BiConsumer)but with a no-op handler.voidsetKnownSolution(Optimisation.Result knownSolution, BiConsumer<ExpressionsBasedModel, Access1D<BigDecimal>> handler) For test/validation during solver development.(package private) voidsetOptimisationSense(Optimisation.Sense optimisationSense) simplify()Will perform pre-solve and then create a copy removing redundant constraint expressions, and pruning the remaining ones to no longer include fixed variables.snapshot()Will create a shallow copy flagged as relaxed.(package private) Structure1D.IntIndextoIntIndex(int index) (package private) Structure2D.IntRowColumntoIntRowColumn(int row, int column) toString()booleanvalidate()This methods validtes model construction only.booleanvalidate(BasicLogger appender) booleanvalidate(Access1D<BigDecimal> solution) booleanvalidate(Access1D<BigDecimal> solution, BasicLogger appender) booleanvalidate(Access1D<BigDecimal> solution, NumberContext context) booleanvalidate(Access1D<BigDecimal> solution, NumberContext context, BasicLogger appender) booleanvalidate(NumberContext context) booleanvalidate(NumberContext context, BasicLogger appender) Returns a stream of variables that are not fixed.voidSave this instance to file.voidwriteTo(InMemoryFile file)
-
Field Details
-
INTEGRATIONS
-
NEW_LINE
- See Also:
-
OBJ_FUNC_AS_CONSTR_KEY
-
OBJECTIVE
- See Also:
-
START_END
- See Also:
-
PRESOLVERS
-
options
-
myExpressions
-
myFixedVariables
-
myForcedIntegration
-
myInfeasible
private transient boolean myInfeasible -
myIntegrationProperties
-
myKnownSolution
-
myObjectiveConstant
-
myOptimisationSense
-
myReferences
-
myRelaxed
private boolean myRelaxed -
myShallowCopy
private final boolean myShallowCopyA shallow copy may share complex/large data structures with other models - typically the Map:s holding Expression parameters. -
myTemporary
Temporary storage for some expression specific subset of variables -
myValidationFailureHandler
-
myVariables
-
myVariablesCategorisation
-
-
Constructor Details
-
ExpressionsBasedModel
public ExpressionsBasedModel() -
ExpressionsBasedModel
-
ExpressionsBasedModel
ExpressionsBasedModel(ExpressionsBasedModel modelToCopy, boolean shallow, boolean prune)
-
-
Method Details
-
addIntegration
public static boolean addIntegration(Optimisation.Integration<ExpressionsBasedModel, ?> integration) Add an integration for a solver that will be used rather than the built-in solvers -
addPresolver
-
clearIntegrations
public static void clearIntegrations() -
clearPresolvers
public static void clearPresolvers() -
isNative
Don't you worry about this! It's for internal use. -
parse
Apart from the "native" EBM file format, currently only supports the MPS file format, but with some of the various extensions. In particular it is possible to parse QP models using QUADOBJ or QMATRIX file sections. -
parse
public static ExpressionsBasedModel parse(InputStream input, ExpressionsBasedModel.FileFormat format) -
removeIntegration
-
removePresolver
-
resetPresolvers
public static void resetPresolvers() -
addExpression
-
addExpression
-
addSpecialOrderedSet
Creates a special ordered set (SOS) presolver instance and links that to the supplied expression. When/if the presolver concludes that the SOS "constraints" are not possible the linked expression is marked as infeasible. -
addSpecialOrderedSet
Calling this method will create 2 things:- A simple expression meassuring the sum of the (binary) variable values (the number of binary
variables that are "ON"). The upper, and optionally lower, limits are set as defined by the
maxandminparameter values. - A custom presolver (specific to this SOS) to be used by the MIP solver. This presolver help to keep track of which combinations of variable values or feasible, and is the only thing that enforces the order.
- Parameters:
orderedSet- The set members in correct order. Each of these variables must be binary.min- The minimum number of binary varibales in the set that must be "ON" (Set this to 0 if there is no minimum.)max- The SOS type or maximum number of binary varibales in the set that may be "ON"
- A simple expression meassuring the sum of the (binary) variable values (the number of binary
variables that are "ON"). The upper, and optionally lower, limits are set as defined by the
-
addVariable
-
addVariable
-
bounds
-
checkSimilarity
-
constraints
Returns a prefiltered stream of expressions that are constraints and have not been markes as redundant. -
copy
-
copy
-
copy
-
countExpressions
public int countExpressions() -
countVariables
public int countVariables() -
describe
Counts variables and expressions of different categories. -
dispose
public void dispose()Description copied from interface:Optimisation.ModelCleanup when a model instance is no longer needed.- Specified by:
disposein interfaceOptimisation.Model
-
getExpression
-
getExpressions
-
getFixedVariables
-
getFreeVariables
-
getIntegerVariables
-
getNegativeVariables
-
getOptimisationSense
- The default optimisation sense is
Optimisation.Sense.MIN - If this model was read from a file and that file format contained information about being a minimisation or maximisation model, that info is reflected here.
- In general you are expected to know whether to call
minimise()ormaximise(). Once you have called one of those methods this method's return value will match that.
- The default optimisation sense is
-
getPositiveVariables
-
getVariable
-
getVariable
-
getVariables
-
getVariableValues
-
getVariableValues
Null variable values are replaced with 0.0. If any variable value is null the state is set to INFEASIBLE even if zero would actually be a feasible value. The objective function value is not calculated for infeasible variable values. -
indexOf
-
indexOfFreeVariable
public int indexOfFreeVariable(int globalIndex) - Parameters:
globalIndex- General, global, variable index- Returns:
- Local index among the free variables. -1 indicates the variable is not a free variable.
-
indexOfFreeVariable
-
indexOfFreeVariable
-
indexOfIntegerVariable
public int indexOfIntegerVariable(int globalIndex) - Parameters:
globalIndex- General, global, variable index- Returns:
- Local index among the integer variables. -1 indicates the variable is not an integer variable.
-
indexOfIntegerVariable
-
indexOfIntegerVariable
-
indexOfNegativeVariable
public int indexOfNegativeVariable(int globalIndex) - Parameters:
globalIndex- General, global, variable index- Returns:
- Local index among the negative variables. -1 indicates the variable is not a negative variable.
-
indexOfNegativeVariable
-
indexOfNegativeVariable
-
indexOfPositiveVariable
public int indexOfPositiveVariable(int globalIndex) - Parameters:
globalIndex- General, global, variable index- Returns:
- Local index among the positive variables. -1 indicates the variable is not a positive variable.
-
indexOfPositiveVariable
-
indexOfPositiveVariable
-
isAnyConstraintQuadratic
public boolean isAnyConstraintQuadratic() -
isAnyExpressionQuadratic
public boolean isAnyExpressionQuadratic()Objective or any constraint has quadratic part. -
isAnyObjectiveQuadratic
public boolean isAnyObjectiveQuadratic() -
isAnyVariableFixed
public boolean isAnyVariableFixed() -
isAnyVariableInteger
public boolean isAnyVariableInteger() -
limitObjective
-
maximise
- Specified by:
maximisein interfaceOptimisation.Model
-
maximise
public <S extends Optimisation.Solver> Optimisation.Result maximise(ExpressionsBasedModel.Integration<S> forcedIntegration) -
minimise
- Specified by:
minimisein interfaceOptimisation.Model
-
minimise
public <S extends Optimisation.Solver> Optimisation.Result minimise(ExpressionsBasedModel.Integration<S> forcedIntegration) -
newExpression
-
newVariable
-
objective
This is generated on demand – you should not cache this. More specifically, modifications made to this expression will not be part of the optimisation model. You define the objective by setting theModelEntity.weight(Comparable)/ModelEntity.weight(Comparable)on one or more variables and/or expressions.- Returns:
- The generated/aggregated objective function
-
prepare
The general recommendation is to NOT call this method directly. Instead you should use/call
maximise()orminimise().The primary use case for this method is as a callback method for solvers that iteratively modifies the model and solves at each iteration point.
With direct usage of this method:
- Maximisation/Minimisation is undefined (you don't know which it is)
- The solution is not written back to the model
- The solution is not validated by the model
-
reduce
Will try to identify constraints with equal variable sets, and check if those can be combined or not. This is a relatively slow process with small chance to actually achieve anything. Therefore it is not part of the default pre-solve andsimplify()functionality.This is an in-place operation. The returned model is the same as this – just to allow chained invocation.
- See Also:
-
relax
public void relax() -
relax
public void relax(boolean soft) - Parameters:
soft- If true the integer variables are still identified as such, but the model is flagged as non-integer (will not use theIntegerSolver, but presolve and validation may still recognise the variables' integer property). If false the integer property of any/all variables are removed.
-
removeExpression
-
setKnownSolution
Same assetKnownSolution(org.ojalgo.optimisation.Optimisation.Result, BiConsumer)but with a no-op handler. -
setKnownSolution
public void setKnownSolution(Optimisation.Result knownSolution, BiConsumer<ExpressionsBasedModel, Access1D<BigDecimal>> handler) For test/validation during solver development.- Parameters:
knownSolution- The optimal solutionhandler- What to do if validation fails
-
simplify
Will perform pre-solve and then create a copy removing redundant constraint expressions, and pruning the remaining ones to no longer include fixed variables.Note that the fixed variables themselves are not removed. They are still present, but fixed, and not used in any expression.
-
snapshot
Will create a shallow copy flagged as relaxed. -
toString
-
validate
public boolean validate()This methods validtes model construction only. All the other validate(...) method validates the solution (one way or another).- Specified by:
validatein interfaceOptimisation.Model- Returns:
- true If eveything is ok. false The model is structurally ok, but the "value" breaks constraints - the solution is infeasible.
- See Also:
-
validate
-
validate
-
validate
-
validate
-
validate
-
validate
-
validate
-
variables
-
writeTo
Save this instance to file. The file format isExpressionsBasedModel.FileFormat.EBMand the file name is therefore recommended to end with ".ebm".- Parameters:
file- The path/name of the file to write.
-
writeTo
-
optimise
private Optimisation.Result optimise(Optimisation.Sense sense, ExpressionsBasedModel.Integration<?> forcedIntegration) -
scanEntities
private void scanEntities() -
addObjectiveConstant
-
addReference
-
deriveAdjustmentRange
-
expressions
Stream<Expression> expressions() -
getIntegration
ExpressionsBasedModel.Integration<?> getIntegration() -
getKnownSolution
Optimisation.Result getKnownSolution() -
getObjectiveConstant
BigDecimal getObjectiveConstant() -
getReferences
Set<Structure1D.IntIndex> getReferences() -
getValidationFailureHandler
BiConsumer<ExpressionsBasedModel, Access1D<BigDecimal>> getValidationFailureHandler() -
isFixed
boolean isFixed() -
isInfeasible
boolean isInfeasible() -
isInteger
-
isIntegrationSwitch
-
isReferenced
-
isRelaxed
boolean isRelaxed() -
isShallowCopy
boolean isShallowCopy() -
isUnbounded
boolean isUnbounded() -
presolve
void presolve() -
setInfeasible
void setInfeasible() -
setIntegrationSwitch
-
setOptimisationSense
-
toIntIndex
-
toIntRowColumn
-