From 278164f80a3f30b76f3e6631245c26fe60d51551 Mon Sep 17 00:00:00 2001 From: odow Date: Wed, 9 Feb 2022 14:22:30 +1300 Subject: [PATCH 1/2] [Utilities] move CachingOptimizer to internal constructors --- src/Utilities/cachingoptimizer.jl | 121 +++++++++++++++++------------- 1 file changed, 70 insertions(+), 51 deletions(-) diff --git a/src/Utilities/cachingoptimizer.jl b/src/Utilities/cachingoptimizer.jl index 5c9c16d3bf..612167b157 100644 --- a/src/Utilities/cachingoptimizer.jl +++ b/src/Utilities/cachingoptimizer.jl @@ -9,21 +9,52 @@ @enum CachingOptimizerState NO_OPTIMIZER EMPTY_OPTIMIZER ATTACHED_OPTIMIZER @enum CachingOptimizerMode MANUAL AUTOMATIC -# TODO: Benchmark to check if CachingOptimizer should be parameterized on the ModelLike type. - """ CachingOptimizer -`CachingOptimizer` is an intermediate layer that stores a cache of the model -and links it with an optimizer. It supports incremental model -construction and modification even when the optimizer doesn't. +`CachingOptimizer` is an intermediate layer that stores a cache of the model and +links it with an optimizer. It supports incremental model construction and +modification even when the optimizer doesn't. + +## Constructors -A `CachingOptimizer` may be in one of three possible states (`CachingOptimizerState`): +```julia + CachingOptimizer(cache::MOI.ModelLike, optimizer::AbstractOptimizer) +``` + +Creates a `CachingOptimizer` in `AUTOMATIC` mode, with the optimizer +`optimizer`. + +The type of the optimizer returned is +`CachingOptimizer{typeof(optimizer), typeof(cache)}` so it does not support the +function `reset_optimizer(::CachingOptimizer, new_optimizer)` if the type of +`new_optimizer` is different from the type of `optimizer`. + +```julia + CachingOptimizer(cache::MOI.ModelLike, mode::CachingOptimizerMode) +``` + +Creates a `CachingOptimizer` in the `NO_OPTIMIZER` state and mode `mode`. + +The type of the optimizer returned is +`CachingOptimizer{MOI.AbstractOptimizer,typeof(cache)}` so it _does_ support the +function `reset_optimizer(::CachingOptimizer, new_optimizer)` if the type of +`new_optimizer` is different from the type of `optimizer`. + +## About the type + +### States + +A `CachingOptimizer` may be in one of three possible states +(`CachingOptimizerState`): * `NO_OPTIMIZER`: The CachingOptimizer does not have any optimizer. * `EMPTY_OPTIMIZER`: The CachingOptimizer has an empty optimizer. The optimizer is not synchronized with the cached model. -* `ATTACHED_OPTIMIZER`: The CachingOptimizer has an optimizer, and it is synchronized with the cached model. +* `ATTACHED_OPTIMIZER`: The CachingOptimizer has an optimizer, and it is + synchronized with the cached model. + +### modes A `CachingOptimizer` has two modes of operation (`CachingOptimizerMode`): @@ -37,31 +68,45 @@ A `CachingOptimizer` has two modes of operation (`CachingOptimizerMode`): perform a modification not supported by the optimizer results in a drop to `EMPTY_OPTIMIZER` mode. """ -mutable struct CachingOptimizer{OptimizerType,ModelType<:MOI.ModelLike} <: - MOI.AbstractOptimizer - optimizer::Union{Nothing,OptimizerType} - model_cache::ModelType +mutable struct CachingOptimizer{O,M<:MOI.ModelLike} <: MOI.AbstractOptimizer + optimizer::Union{Nothing,O} + model_cache::M state::CachingOptimizerState mode::CachingOptimizerMode model_to_optimizer_map::IndexMap optimizer_to_model_map::IndexMap # CachingOptimizer externally uses the same variable and constraint indices - # as the model_cache. model_to_optimizer_map maps from the model_cache indices to the - # optimizer indices. -end + # as the model_cache. model_to_optimizer_map maps from the model_cache + # indices to the optimizer indices. -function CachingOptimizer( - model_cache::MOI.ModelLike, - mode::CachingOptimizerMode, -) - return CachingOptimizer{MOI.AbstractOptimizer,typeof(model_cache)}( - nothing, - model_cache, - NO_OPTIMIZER, - mode, - IndexMap(), - IndexMap(), + function CachingOptimizer( + cache::MOI.ModelLike, + mode::CachingOptimizerMode, ) + return new{MOI.AbstractOptimizer,typeof(cache)}( + nothing, + cache, + NO_OPTIMIZER, + mode, + IndexMap(), + IndexMap(), + ) + end + + function CachingOptimizer( + cache::MOI.ModelLike, + optimizer::MOI.AbstractOptimizer, + ) + @assert MOI.is_empty(optimizer) + return new{typeof(optimizer),typeof(cache)}( + optimizer, + cache, + EMPTY_OPTIMIZER, + AUTOMATIC, + IndexMap(), + IndexMap(), + ) + end end function Base.show(io::IO, C::CachingOptimizer) @@ -75,32 +120,6 @@ function Base.show(io::IO, C::CachingOptimizer) return show(IOContext(io, :indent => get(io, :indent, 0) + 2), C.optimizer) end -""" - CachingOptimizer(model_cache::MOI.ModelLike, optimizer::AbstractOptimizer) - -Creates an `CachingOptimizer` in `AUTOMATIC` mode, with the optimizer -`optimizer`. - -The type of the optimizer returned is `CachingOptimizer{typeof(optimizer), -typeof(model_cache)}` so it does not support the function -`reset_optimizer(::CachingOptimizer, new_optimizer)` if the type of -`new_optimizer` is different from the type of `optimizer`. -""" -function CachingOptimizer( - model_cache::MOI.ModelLike, - optimizer::MOI.AbstractOptimizer, -) - @assert MOI.is_empty(optimizer) - return CachingOptimizer{typeof(optimizer),typeof(model_cache)}( - optimizer, - model_cache, - EMPTY_OPTIMIZER, - AUTOMATIC, - IndexMap(), - IndexMap(), - ) -end - ## Methods for managing the state of CachingOptimizer. """ From a600aea67fe0669163a07f6aa4d428b1f1d95251 Mon Sep 17 00:00:00 2001 From: Oscar Dowson Date: Wed, 9 Feb 2022 14:27:11 +1300 Subject: [PATCH 2/2] Update cachingoptimizer.jl --- src/Utilities/cachingoptimizer.jl | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/src/Utilities/cachingoptimizer.jl b/src/Utilities/cachingoptimizer.jl index 612167b157..faf4b56ec9 100644 --- a/src/Utilities/cachingoptimizer.jl +++ b/src/Utilities/cachingoptimizer.jl @@ -79,10 +79,7 @@ mutable struct CachingOptimizer{O,M<:MOI.ModelLike} <: MOI.AbstractOptimizer # as the model_cache. model_to_optimizer_map maps from the model_cache # indices to the optimizer indices. - function CachingOptimizer( - cache::MOI.ModelLike, - mode::CachingOptimizerMode, - ) + function CachingOptimizer(cache::MOI.ModelLike, mode::CachingOptimizerMode) return new{MOI.AbstractOptimizer,typeof(cache)}( nothing, cache,