Transformation Backends
A technical manual for optimizing (solving) InfiniteOpt models via transformation backends. See the respective guide for more information.
Optimize
JuMP.optimize! — MethodJuMP.optimize!(model::InfiniteModel; [kwargs...])Extend JuMP.optimize! to optimize infinite models using the internal transformation backend. Calls build_transformation_backend! if the optimizer model isn't up-to-date. The kwargs correspond to keyword arguments passed to build_transformation_backend! if any are defined. The kwargs can also include arguments that are passed to an optimize hook if one was set with JuMP.set_optimize_hook. Typically, this returns nothing, but certain backends may return something.
Example
julia> optimize!(model)
julia> has_values(model)
trueBackend Settings/Queries
InfiniteOpt.transformation_model — Methodtransformation_model(model::InfiniteModel)Return the underlying model used by the transformation backend.
Example
julia> trans_model = transformation_model(model)
A JuMP Model
├ solver: none
├ objective_sense: FEASIBILITY_SENSE
├ num_variables: 0
├ num_constraints: 0
└ Names registered in the model: noneInfiniteOpt.transformation_data — Methodtransformation_data(model::InfiniteModel)Return the underlying data (typically mapping data) used by the transformation backend.
Example
julia> mapping_data = transformation_data(model);InfiniteOpt.transformation_backend — Functiontransformation_backend(
model::InfiniteModel
)::AbstractTransformationBackendRetrieve the transformation backend used by the model.
Example
julia> transformation_backend(model)
A TranscriptionBackend that uses a
A JuMP Model
├ solver: none
├ objective_sense: FEASIBILITY_SENSE
├ num_variables: 0
├ num_constraints: 0
└ Names registered in the model: noneInfiniteOpt.set_transformation_backend — Functionset_transformation_backend(
model::InfiniteModel,
backend::AbstractTransformationBackend
)::NothingSpecify a new transformation backend backend for the model. Note that all data/settings/results associated with the previous backend will be removed.
Example
julia> transformation_backend(model)
A TranscriptionBackend that uses a
A JuMP Model
├ solver: none
├ objective_sense: FEASIBILITY_SENSE
├ num_variables: 0
├ num_constraints: 0
└ Names registered in the model: none
julia> set_transformation_backend(model, TranscriptionBackend(Ipopt.Optimizer))
julia> transformation_backend(model)
A TranscriptionBackend that uses a
A JuMP Model
├ solver: Ipopt
├ objective_sense: FEASIBILITY_SENSE
├ num_variables: 0
├ num_constraints: 0
└ Names registered in the model: noneInfiniteOpt.build_transformation_backend! — Methodbuild_transformation_backend!(model::InfiniteModel; [kwargs...])::NothingBuild the model used by the underlying transformation backend stored in model such that it is ready to solve. Specifically, translate the InfiniteOpt formulation stored in model into (typically an appoximate) formulation that is compatible with the backend. This is called automatically by optimize!; however, it this method can be used to build the transformation backend without solving it.
Example
julia> build_transformation_backend!(model)
julia> transformation_backend_ready(model)
trueInfiniteOpt.transformation_variable — Methodtransformation_variable(vref::GeneralVariableRef; [kwargs...])Returns the variable(s) used by the transformation backend to represent vref. Certain backends may also allow the use of keyward arguments.
The default backend TranscriptionOpt uses the keyword arguments:
label::Type{<:AbstractSupportLabel} = PublicLabel
By default only variables corresponding to public supports are returned, the full set can be accessed via label = All. Where possible, all the transcripted variables of infinite variables are returned as an n-dimensional array where each dimension is determined by the each independent group of infinite parameters it depends on.
Example
julia> transformation_variable(x) # infinite variable
2-element Array{VariableRef,1}:
x(0.0)
x(1.0)
julia> transformation_variable(z) # finite variable
zInfiniteOpt.transformation_expression — Methodtransformation_expression(
expr::JuMP.AbstractJuMPScalar;
[label::Type{<:AbstractSupportLabel} = PublicLabel,
kwargs...]
)Return the reformulation expression(s) stored in the transformation backend that correspond to expr. Also errors if no such expression can be found in the transformation backend (meaning one or more of the underlying variables have not been transformed).
The keyword argument label is what TranscriptionOpt employs and kwargs denote extra ones that user extensions may employ in accordance with their implementation of transformation_expression. Errors if such an extension has not been written.
By default only the expressions associated with public supports are returned, the full set can be accessed via label = All. Where possible, all the transformed expressions are returned as an n-dimensional array where each dimension is determined by the each independent group of infinite parameters it depends on. The corresponding supports are obtained via supports using the same keyword arguments.
Example
julia> transformation_expression(my_expr) # finite expression
x(0.0) - yInfiniteOpt.transformation_constraint — Methodtransformation_constraint(
cref::InfOptConstraintRef;
[label::Type{<:AbstractSupportLabel} = PublicLabel,
kwargs...]
)Return the reformulation constraint(s) stored in the transformation backend that correspond to cref. Errors if no such constraint can be found in the transformation backend.
The keyword argument label is what TranscriptionOpt employs and kwargs denote extra ones that user extensions may employ in accordance with their implementation of transformation_constraint. Errors if such an extension has not been written.
By default only the constraints associated with public supports are returned, the full set can be accessed via label = All. Where possible, all the transformed cosntraints are returned as an n-dimensional array where each dimension is determined by the each independent group of infinite parameters it depends on. The corresponding supports are obtained via supports using the same keyword arguments.
Example
julia> transformation_constraint(c1) # finite constraint
c1 : x(0.0) - y <= 3.0InfiniteOpt.supports — Methodsupports(
vref::DecisionVariableRef;
[label::Type{<:AbstractSupportLabel} = PublicLabel,
kwargs...]
)::Vector{<:Tuple}Return the supports associated with vref in the transformation model. Errors if InfiniteOpt.variable_supports has not been extended for the transformation backend type or if vref is not reformulated in the transformation backend.
The keyword argument label is what TranscriptionOpt employs and kwargs denote extra ones that user extensions may employ in accordance with their implementation of variable_supports. Errors if such an extension has not been written.
By default only the public supports are returned, the full set can be accessed via label = All. Where possible, all the supports of infinite variables are returned as an n-dimensional array where each dimension is determined by the each independent group of infinite parameters it depends on.
Example
julia> supports(vref)
2-element Array{Tuple{Float64},1}:
(0.0,)
(1.0,)InfiniteOpt.supports — Methodsupports(
expr::JuMP.AbstractJuMPScalar;
[label::Type{<:AbstractSupportLabel} = PublicLabel,
kwargs...]
)Return the support associated with expr. Errors if expr is not associated with the constraint mappings stored in the transformation backend.
The keyword arguments label is what TranscriptionOpt employs and kwargs denote extra ones that user extensions may employ in accordance with their implementation of expression_supports. Errors if such an extension has not been written.
By default only the public supports are returned, the full set can be accessed via label = All. Where possible, all the supports of an infinite expression are returned as an n-dimensional array where each dimension is determined by the each independent group of infinite parameters it depends on.
Example
julia> supports(cref)
2-element Array{Tuple{Float64},1}:
(0.0,)
(1.0,)InfiniteOpt.supports — Methodsupports(cref::InfOptConstraintRef;
[label::Type{<:AbstractSupportLabel} = PublicLabel,
kwargs...])Return the support associated with cref. Errors if cref is not associated with the constraint mappings stored in the transformation backend.
The keyword argument label is what TranscriptionOpt employs and kwargs denote extra ones that user extensions may employ in accordance with their implementation of constraint_supports. Errors if such an extension has not been written.
By default only the public supports are returned, the full set can be accessed via label = All. Where possible, all the supports of the constraint are returned as an n-dimensional array where each dimension is determined by the each independent group of infinite parameters it depends on.
Example
julia> supports(cref)
2-element Array{Tuple{Float64},1}:
(0.0,)
(1.0,)JuMP.set_optimizer — MethodJuMP.set_optimizer(
model::InfiniteModel,
[optimizer_constructor;
add_bridges::Bool = true,
kwargs...]
)Extend JuMP.set_optimizer to set optimizer used by the underlying transformation backend associated with model. If a backend uses JuMP then add_bridges can be used as a keyword argument.
Example
julia> set_optimizer(model, HiGHS.Optimizer)
julia> transformation_model(model)
A JuMP Model
├ solver: HiGHS
├ objective_sense: FEASIBILITY_SENSE
├ num_variables: 0
├ num_constraints: 0
└ Names registered in the model: noneJuMP.set_silent — MethodJuMP.set_silent(model::InfiniteModel)Extend JuMP.set_silent to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.set_attribute with attribute MathOptInterface.Silent().
JuMP.unset_silent — MethodJuMP.unset_silent(model::InfiniteModel)Extend JuMP.unset_silent to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.set_attribute with attribute MathOptInterface.Silent().
JuMP.set_time_limit_sec — MethodJuMP.set_time_limit_sec(model::InfiniteModel, value::Real)Extend JuMP.set_time_limit_sec to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.set_attribute with attribute MOI.TimeLimitSec().
JuMP.unset_time_limit_sec — MethodJuMP.unset_time_limit_sec(model::InfiniteModel)Extend JuMP.unset_time_limit_sec to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.set_attribute with attribute MathOptInterface.TimeLimitSec().
JuMP.time_limit_sec — MethodJuMP.time_limit_sec(model::InfiniteModel)Extend JuMP.time_limit_sec to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.get_attribute with attribute MathOptInterface.TimeLimitSec().
JuMP.solver_name — MethodJuMP.solver_name(model::InfiniteModel)Extend JuMP.solver_name to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.get_attribute with attribute MathOptInterface.SolverName().
JuMP.mode — MethodJuMP.mode(model::InfiniteModel)Extend JuMP.mode to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.mode.
JuMP.compute_conflict! — MethodJuMP.compute_conflict!(model::InfiniteModel)Extend JuMP.compute_conflict! to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.compute_conflict!.
JuMP.copy_conflict — MethodJuMP.copy_conflict(model::InfiniteModel)Extend JuMP.copy_conflict to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.copy_conflict.
JuMP.bridge_constraints — MethodJuMP.bridge_constraints(model::InfiniteModel)Extend JuMP.bridge_constraints to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.bridge_constraints.
JuMP.add_bridge — MethodJuMP.add_bridge(model::InfiniteModel, value)Extend JuMP.add_bridge to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.add_bridge.
JuMP.print_active_bridges — MethodJuMP.print_active_bridges([io::IO = stdout,] model::InfiniteModel)
JuMP.print_active_bridges([io::IO = stdout,] model::InfiniteModel, ::Type{<:JuMP.AbstractJuMPScalar})
JuMP.print_active_bridges([io::IO = stdout,] model::InfiniteModel, ::Type{<:JuMP.AbstractJuMPScalar}, ::Type{<:MOI.AbstractSet})
JuMP.print_active_bridges([io::IO = stdout,] model::InfiniteModel, ::Type{<:MOI.AbstractSet})Extend JuMP.print_active_bridges to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.print_active_bridges.
JuMP.print_bridge_graph — MethodJuMP.print_bridge_graph([io::IO = stdout,] model::InfiniteModel)Extend JuMP.print_bridge_graph to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.print_bridge_graph.
JuMP.set_attribute — MethodJuMP.set_attribute(model::InfiniteModel, attr, value)::NothingSpecify an attribute attr to the transformation backend of model. Typically, this corresponds to MOI.AbstractOptimizerAttributes.
Example
julia> set_attribute(model, MOI.TimeLimitSec(), 42.0)JuMP.set_attributes — FunctionJuMP.set_attributes(model::InfiniteModel, pairs::Pair...)::NothingSpecify multiple optimizer transformation backend attributes as Pairs of the form attr => value which are used for set_attribute(model, attr, value).
Example
julia> set_attributes(model, "tol" => 1e-4, "max_iter" => 100)JuMP.get_attribute — MethodJuMP.get_attribute(model::InfiniteModel, attr)Retrieve an attribute attr from the transformation backend of model. Typically, this corresponds to MOI.AbstractOptimizerAttributes.
Example
julia> get_attribute(model, MOI.TimeLimitSec())
60.0JuMP.backend — MethodJuMP.backend(model::InfiniteModel)Extend JuMP.backend to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.backend.
JuMP.unsafe_backend — MethodJuMP.unsafe_backend(model::InfiniteModel)Extend JuMP.unsafe_backend to accept InfiniteModels. This relies on the underlying transformation backend supporting JuMP.unsafe_backend.
Transformation Backend API
InfiniteOpt.AbstractTransformationBackend — TypeAbstractTransformationBackendAbstract type for transformation backends to InfiniteModels. Any user-defined backend type should inherit this type.
InfiniteOpt.JuMPBackend — TypeJuMPBackend{TAG <: AbstractJuMPTag, T, D} <: AbstractTransformationBackendA transformation backend type for transformation backends that use JuMP Models. This serves as the main extension point for defining new JuMP-based backends. In which case a new AbstractJuMPTag should be made with which the JuMPBackend is created:
backend = JuMPBackend{MyTag}(model::JuMP.GenericModel, data)where data stores information used by the backend (typically mapping information to the overlying InfiniteModel).
The JuMP Model can be accessed by transformation_model and the data can be retrieved via transformation_data.
InfiniteOpt.AbstractJuMPTag — TypeAbstractJuMPTagAbstract type to enable dispatch between differnent transformation backends that use the extension API provided by JuMPBackend.
InfiniteOpt.transformation_model — Methodtransformation_model(backend::AbstractTransformationBackend)Return the underlying model used by the backend. This serves as an extension point for new backend types. No extension is needed for JuMPBackends.
InfiniteOpt.transformation_data — Methodtransformation_data(backend::AbstractTransformationBackend)Return the underlying data (typically mapping data) used by the backend. This serves as an extension point for new backend types. No extension is needed for JuMPBackends.
JuMP.get_attribute — MethodJuMP.get_attribute(backend::AbstractTransformationBackend, attr)Retrieve some attribute attr from the backend. This is a general purpose method typically used to query optimizer related information. This serves as an extension point for new backend types. New backends should include extensions for the following attributes as appropriate: - MOI.Silent - MOI.TimeLimitSec - MOI.RawOptimizerAttribute - MOI.SolverName - MOI.TerminationStatus - MOI.RawStatusString - MOI.PrimalStatus - MOI.DualStatus - MOI.SolveTimeSec - MOI.ResultCount - MOI.SimplexIterations - MOI.BarrierIterations - MOI.NodeCount - MOI.ObjectiveBound - MOI.RelativeGap - MOI.ObjectiveValue - MOI.DualObjectiveValue
No extension is needed for JuMPBackends.
JuMP.set_attribute — MethodJuMP.set_attribute(backend::AbstractTransformationBackend, attr, value)::NothingSpecify some attribute attr to the backend. This is a general purpose method typically used to set optimizer related information. This serves as an extension point for new backend types. New backends should include extensions for attributes of type: - MOI.Silent - MOI.TimeLimitSec - MOI.RawOptimizerAttribute
No extension is needed for JuMPBackends.
Base.empty! — MethodBase.empty!(backend::AbstractTransformationBackend)Empty backend of all its contents. For new backend types, this needs to be defined such that empty!(model::InfiniteModel) works. For JuMPBackends this defaults to
empty!(transformation_model(backend))
empty!(transformation_data(backend))InfiniteOpt.build_transformation_backend! — Methodbuild_transformation_backend!(
model::InfiniteModel,
backend::AbstractTransformationBackend;
[kwargs...]
)::NothingGiven model, transform it into the representation used by backend. Once completed, backend should be ready to be solved. This serves as an extension point for new types of backends. If needed, keyword arguments can be added. Typically, this should clear out the backend before reconstructing it.
JuMP.optimize! — MethodJuMP.optimize!(backend::AbstractTransformationBackend)Invoke the relevant routines to solve the underlying model used by backend. Note that build_transformation_backend! will be called before this method is. This needs to be extended for new backend types, but no extension is needed for JuMPBackends. Optionally, information can be returned if desired.
JuMP.set_optimizer — MethodJuMP.set_optimizer(
backend::AbstractTransformationBackend,
optimizer_constructor;
[kwargs...]
)::NothingSpecify the optimizer optimizer_constructor that should be used by backend. This is intended as an extension point for new transformation backend types. Keyword arguments can be added as needed. No extension is necessary for JuMPBackends.
JuMP.mode — MethodJuMP.mode(backend::AbstractTransformationBackend)Implement JuMP.mode for transformation backends. If applicable, this should be extended for new backend types. No extension is needed for JuMPBackends.
JuMP.compute_conflict! — MethodJuMP.compute_conflict!(backend::AbstractTransformationBackend)Implement JuMP.compute_conflict! for transformation backends. If applicable, this should be extended for new backend types. No extension is needed for JuMPBackends.
JuMP.copy_conflict — MethodJuMP.copy_conflict(backend::AbstractTransformationBackend)Implement JuMP.copy_conflict for transformation backends. If applicable, this should be extended for new backend types. No extension is needed for JuMPBackends.
JuMP.bridge_constraints — MethodJuMP.bridge_constraints(backend::AbstractTransformationBackend)Implement JuMP.bridge_constraints for transformation backends. If applicable, this should be extended for new backend types. No extension is needed for JuMPBackends.
JuMP.add_bridge — MethodJuMP.add_bridge(backend::AbstractTransformationBackend, value)Implement JuMP.add_bridge for transformation backends. If applicable, this should be extended for new backend types. No extension is needed for JuMPBackends.
JuMP.print_active_bridges — MethodJuMP.print_active_bridges(
io::IO,
backend::AbstractTransformationBackend,
args...
)Implment JuMP.print_active_bridges for transformation backends. If applicable, this should be extended for new backend types. No extension is needed for JuMPBackends. Here, args can be one of the following:
- empty (print all the bridges)
- the objective type (print the objective bridges)
- a function type and set type from a constraint
- a constraint set type
JuMP.print_bridge_graph — MethodJuMP.print_bridge_graph(
io::IO,
backend::AbstractTransformationBackend
)Implment JuMP.print_bridge_graph for transformation backends. If applicable, this should be extended for new backend types. No extension is needed for JuMPBackends.
JuMP.backend — MethodJuMP.backend(backend::AbstractTransformationBackend)Implement JuMP.backend for transformation backends. If applicable, this should be extended for new backend types. No extension is needed for JuMPBackends.
JuMP.unsafe_backend — MethodJuMP.unsafe_backend(backend::AbstractTransformationBackend)Implement JuMP.unsafe_backend for transformation backends. If applicable, this should be extended for new backend types. No extension is needed for JuMPBackends.
InfiniteOpt.transformation_variable — Methodtransformation_variable(
vref::GeneralVariableRef,
backend::AbstractTransformationBackend;
[kwargs...]
)Return the variable(s) that map to vref used by backend. This serves as an extension point for new backend types. If needed, keywords arguments can be added.
InfiniteOpt.transformation_expression — Methodtransformation_expression(expr, backend::AbstractTransformationBackend; [kwargs...])Return the reformulation expression(s) stored in the transformation backend that correspond to expr. This needs to be defined for extensions that implement a new AbstractTransformationBackend. Keyword arguments can be added as needed. Note that if expr is a GeneralVariableRef this just dispatches to transformation_variable.
InfiniteOpt.transformation_constraint — Methodtransformation_constraint(
cref::InfOptConstraintRef,
backend::AbstractTransformationBackend;
[kwargs...]
)Return the reformulation constraint(s) stored in the transformation backend that correspond to cref. This needs to be defined for extensions that implement a custom transformation backend type. Keyword arguments can be added as needed.
InfiniteOpt.variable_supports — Methodvariable_supports(
vref::DecisionVariableRef,
backend::AbstractTransformationBackend;
[kwargs...]
)Return the supports associated with the mappings of vref in backend. This dispatches off of backend which permits transformation backend extensions. This should throw an error if vref is not associated with the variable mappings stored in backend. Keyword arguments can be added as needed. Note that no extension is necessary for point or finite variables.
InfiniteOpt.expression_supports — Methodexpression_supports(
expr,
backend::AbstractTransformationBackend;
[kwargs...]
)Return the supports associated with the mappings of expr in backend. This should throw an error if expr is not associated with the variable mappings stored in backend. Keyword arguments can be added as needed. Note that if expr is a GeneralVariableRef this just dispatches to variable_supports.
InfiniteOpt.constraint_supports — Methodconstraint_supports(
cref::InfOptConstraintRef
backend::AbstractTransformationBackend;
[kwargs...]
)Return the supports associated with the mappings of cref in backend. This should throw an error if cref is not associated with the variable mappings stored in backend. Keyword arguments can be added as needed.
InfiniteOpt.transformation_backend_ready — Functiontransformation_backend_ready(model::InfiniteModel)::BoolReturn Bool if the transformation backend model is up-to-date with model and ready to be optimized.
Example
julia> transformation_backend_ready(model)
falseInfiniteOpt.set_transformation_backend_ready — Functionset_transformation_backend_ready(model::InfiniteModel, status::Bool)::NothingSet the status of the transformation backend model to whether it is up-to-date or not. Note is more intended as an internal function, but is useful for extensions.
Example
julia> set_transformation_backend_ready(model, true)
julia> transformation_backend_ready(model)
trueInfiniteOpt.update_parameter_value — Methodupdate_parameter_value(
backend::AbstractTransformationBackend,
ref::Union{FiniteParameterRef, ParameterFunctionRef},
value
)::BoolIf backendis built, then this method updates whatrefcorresponds to in thebackendtovalue, then it returns aBoolon whether the update was successful. This is intended as an extension point for newAbstractTransformationBackends to more efficiently handle parameter updates for resolves. This defaults tofalse, meaning that no update occurs (forcing the backend to be rebuilt). Users should use [JuMP.setparametervalue`](@ref) rather than call this method directly.
InfiniteOpt.warmstart_backend_start_values — Methodwarmstart_backend_start_values(
backend::AbstractTransformationBackend;
[kwargs...]
)::NothingUse the previous solution values stored in backend to warmstart the start values to be used for the next optimize! call. This serves as an extension point for new backend types.