From 516b23040ff89fda014a44e3a8c966cd467b924c Mon Sep 17 00:00:00 2001 From: Oscar Dowson Date: Wed, 20 Sep 2023 21:34:35 +1200 Subject: [PATCH] Fix various JET errors (#2276) --- .../Constraint/bridges/all_different_reif.jl | 13 ++++---- .../Constraint/bridges/set_dot_scaling.jl | 5 +-- src/Bridges/Constraint/map.jl | 2 +- src/Bridges/Variable/map.jl | 18 ++++++----- src/Bridges/bridge_optimizer.jl | 9 ++++-- src/Bridges/lazy_bridge_optimizer.jl | 31 ++++++++++++------- src/FileFormats/MOF/read.jl | 8 +++-- src/FileFormats/NL/sol.jl | 25 ++++++++------- .../ReverseAD/mathoptinterface_api.jl | 27 +++++++++------- src/Nonlinear/evaluator.jl | 17 +++++----- src/Utilities/copy.jl | 6 ++-- src/Utilities/functions.jl | 20 ++++++++++-- src/Utilities/matrix_of_constraints.jl | 2 +- src/Utilities/model.jl | 4 --- src/Utilities/objective_container.jl | 16 ++++++++-- src/Utilities/parser.jl | 4 +-- src/Utilities/print.jl | 6 ++-- src/Utilities/product_of_sets.jl | 6 ++-- src/Utilities/struct_of_constraints.jl | 2 +- src/Utilities/universalfallback.jl | 2 +- src/Utilities/vector_of_constraints.jl | 14 ++++++--- src/functions.jl | 3 +- 22 files changed, 147 insertions(+), 93 deletions(-) diff --git a/src/Bridges/Constraint/bridges/all_different_reif.jl b/src/Bridges/Constraint/bridges/all_different_reif.jl index 86cba1bb7c..21f374bd6b 100644 --- a/src/Bridges/Constraint/bridges/all_different_reif.jl +++ b/src/Bridges/Constraint/bridges/all_different_reif.jl @@ -174,11 +174,11 @@ end function MOI.get( bridge::ReifiedAllDifferentToCountDistinctBridge, ::MOI.ListOfVariableIndices, -)::Vector{MOI.VariableIndex} +) if bridge.y === nothing return MOI.VariableIndex[] end - return [bridge.y] + return MOI.VariableIndex[something(bridge.y)] end function MOI.get( @@ -195,11 +195,12 @@ function MOI.get( bridge::ReifiedAllDifferentToCountDistinctBridge{T}, ::MOI.ListOfConstraintIndices{MOI.VariableIndex,MOI.EqualTo{T}}, ) where {T} - if bridge.y === nothing - return MOI.ConstraintIndex{MOI.VariableIndex,MOI.EqualTo{T}}[] + F, S = MOI.VariableIndex, MOI.EqualTo{T} + ret = MOI.ConstraintIndex{F,S}[] + if bridge.y !== nothing + push!(ret, MOI.ConstraintIndex{F,S}(something(bridge.y).value)) end - ci = MOI.ConstraintIndex{MOI.VariableIndex,MOI.EqualTo{T}}(bridge.y.value) - return [ci] + return ret end function MOI.get( diff --git a/src/Bridges/Constraint/bridges/set_dot_scaling.jl b/src/Bridges/Constraint/bridges/set_dot_scaling.jl index 7c0f209746..0eef72de82 100644 --- a/src/Bridges/Constraint/bridges/set_dot_scaling.jl +++ b/src/Bridges/Constraint/bridges/set_dot_scaling.jl @@ -22,7 +22,8 @@ in `S` to constraints in [`MOI.Scaled{S}`](@ref MOI.Scaled). * `F` in [`MOI.Scaled{S}`](@ref MOI.Scaled) """ -struct SetDotScalingBridge{T,S,F,G} <: SetMapBridge{T,MOI.Scaled{S},S,F,G} +struct SetDotScalingBridge{T,S<:MOI.AbstractVectorSet,F,G} <: + SetMapBridge{T,MOI.Scaled{S},S,F,G} constraint::MOI.ConstraintIndex{F,MOI.Scaled{S}} end @@ -125,7 +126,7 @@ in the `MOI.Scaled{S}` to constraints in the `S`. * `F` in `S` """ -struct SetDotInverseScalingBridge{T,S,F,G} <: +struct SetDotInverseScalingBridge{T,S<:MOI.AbstractVectorSet,F,G} <: SetMapBridge{T,S,MOI.Scaled{S},F,G} constraint::MOI.ConstraintIndex{F,S} end diff --git a/src/Bridges/Constraint/map.jl b/src/Bridges/Constraint/map.jl index 95a6d63e16..38cfbb11d7 100644 --- a/src/Bridges/Constraint/map.jl +++ b/src/Bridges/Constraint/map.jl @@ -86,7 +86,7 @@ function Base.getindex( end function Base.delete!(map::Map, ci::MOI.ConstraintIndex) - _unregister_for_final_touch(map, map.bridges[_index(ci)]) + _unregister_for_final_touch(map, map.bridges[_index(ci)]::AbstractBridge) map.bridges[_index(ci)] = nothing return map end diff --git a/src/Bridges/Variable/map.jl b/src/Bridges/Variable/map.jl index 014c4847b3..7b9e98adb0 100644 --- a/src/Bridges/Variable/map.jl +++ b/src/Bridges/Variable/map.jl @@ -208,7 +208,7 @@ function number_with_set(map::Map, S::Type{<:MOI.AbstractSet}) end function constraint(map::Map, vi::MOI.VariableIndex) - S = constrained_set(map, vi) + S = constrained_set(map, vi)::Type{<:MOI.AbstractSet} F = MOI.Utilities.variable_function_type(S) return MOI.ConstraintIndex{F,S}(-bridge_index(map, vi)) end @@ -235,12 +235,14 @@ Return a list of all the different types `(F, S)` of `F`-in-`S` constraints in function list_of_constraint_types(map::Map) list = Set{Tuple{Type,Type}}() for i in eachindex(map.bridges) - if map.bridges[i] !== nothing - S = map.sets[i] - if S != MOI.Reals - push!(list, (MOI.Utilities.variable_function_type(S), S)) - end + if map.bridges[i] === nothing + continue end + S = map.sets[i] + if S === nothing || S == MOI.Reals + continue + end + push!(list, (MOI.Utilities.variable_function_type(S), S)) end return list end @@ -320,13 +322,13 @@ function add_key_for_bridge( index = -bridge_index variable = MOI.VariableIndex(index) if map.unbridged_function !== nothing - mappings = unbridged_map(map.bridges[bridge_index], variable) + mappings = unbridged_map(something(map.bridges[bridge_index]), variable) if mappings === nothing map.unbridged_function = nothing else for mapping in mappings push!( - map.unbridged_function, + something(map.unbridged_function), mapping.first => (bridge_index, mapping.second), ) end diff --git a/src/Bridges/bridge_optimizer.jl b/src/Bridges/bridge_optimizer.jl index 22aba001c9..c0af0b3440 100644 --- a/src/Bridges/bridge_optimizer.jl +++ b/src/Bridges/bridge_optimizer.jl @@ -1225,7 +1225,7 @@ end function MOI.set( b::AbstractBridgeOptimizer, attr::MOI.AbstractVariableAttribute, - index::MOI.Index, + index::MOI.VariableIndex, value, ) value = bridged_function(b, value) @@ -1240,7 +1240,7 @@ end function MOI.set( b::AbstractBridgeOptimizer, attr::MOI.AbstractVariableAttribute, - indices::Vector{<:MOI.Index}, + indices::Vector{MOI.VariableIndex}, values::Vector, ) if any(index -> is_bridged(b, index), indices) @@ -2004,7 +2004,10 @@ function bridged_variable_function( vi::MOI.VariableIndex, ) if is_bridged(b, vi) - func = bridged_function(bridge(b, vi), _index(b, vi)...) + func = bridged_function( + bridge(b, vi)::Variable.AbstractBridge, + _index(b, vi)..., + ) # If two variable bridges are chained, `func` may still contain # bridged variables. return bridged_function(b, func) diff --git a/src/Bridges/lazy_bridge_optimizer.jl b/src/Bridges/lazy_bridge_optimizer.jl index daac29de41..5bfe1ac29c 100644 --- a/src/Bridges/lazy_bridge_optimizer.jl +++ b/src/Bridges/lazy_bridge_optimizer.jl @@ -128,10 +128,13 @@ end Return the list of `VariableNode` that would be added if `BT` is used in `b`. """ -function _variable_nodes(b::LazyBridgeOptimizer, ::Type{BT}) where {BT} - return VariableNode[ - node(b, S) for (S,) in added_constrained_variable_types(BT) - ] +function _variable_nodes( + b::LazyBridgeOptimizer, + ::Type{BT}, +) where {BT<:AbstractBridge} + return map(added_constrained_variable_types(BT)) do (S,) + return node(b, S)::VariableNode + end end """ @@ -139,7 +142,10 @@ end Return the list of `ConstraintNode` that would be added if `BT` is used in `b`. """ -function _constraint_nodes(b::LazyBridgeOptimizer, ::Type{BT}) where {BT} +function _constraint_nodes( + b::LazyBridgeOptimizer, + ::Type{BT}, +) where {BT<:AbstractBridge} return ConstraintNode[ node(b, F, S) for (F, S) in added_constraint_types(BT) ] @@ -168,10 +174,10 @@ function _edge( ) return ObjectiveEdge( index, - _variable_nodes(b, BT), - _constraint_nodes(b, BT), - node(b, set_objective_function_type(BT)), - bridging_cost(BT), + _variable_nodes(b, BT)::Vector{VariableNode}, + _constraint_nodes(b, BT)::Vector{ConstraintNode}, + node(b, set_objective_function_type(BT))::ObjectiveNode, + bridging_cost(BT)::Float64, ) end @@ -304,7 +310,7 @@ end Return the `ObjectiveNode` associated with constraint `F` in `b`. """ -function node(b::LazyBridgeOptimizer, F::Type{<:MOI.AbstractFunction}) +function node(b::LazyBridgeOptimizer, ::Type{F}) where {F<:MOI.AbstractFunction} # If we support the objective function, the node is 0. if MOI.supports(b.model, MOI.ObjectiveFunction{F}()) return ObjectiveNode(0) @@ -321,7 +327,10 @@ function node(b::LazyBridgeOptimizer, F::Type{<:MOI.AbstractFunction}) push!(b.objective_types, (F,)) for (i, BT) in enumerate(b.objective_bridge_types) if Objective.supports_objective_function(BT, F) - bridge_type = Objective.concrete_bridge_type(BT, F) + bridge_type = Objective.concrete_bridge_type( + BT, + F, + )::Type{<:Objective.AbstractBridge} edge = _edge(b, i, bridge_type)::ObjectiveEdge add_edge(b.graph, objective_node, edge) end diff --git a/src/FileFormats/MOF/read.jl b/src/FileFormats/MOF/read.jl index 368de7959d..78df5254df 100644 --- a/src/FileFormats/MOF/read.jl +++ b/src/FileFormats/MOF/read.jl @@ -297,9 +297,11 @@ function function_to_moi( object::Object, name_map::Dict{String,MOI.VariableIndex}, ) - return MOI.VectorOfVariables([ - name_map[variable] for variable::String in object["variables"] - ]) + return MOI.VectorOfVariables( + MOI.VariableIndex[ + name_map[variable] for variable::String in object["variables"] + ], + ) end # ========== Typed vector functions ========== diff --git a/src/FileFormats/NL/sol.jl b/src/FileFormats/NL/sol.jl index 9d7f9e1967..d6527e6850 100644 --- a/src/FileFormats/NL/sol.jl +++ b/src/FileFormats/NL/sol.jl @@ -111,13 +111,16 @@ function MOI.get( return sol.variable_primal[MOI.VariableIndex(ci.value)] end +# Helper function to assert that the model is not nothing +_model(sol::SolFileResults) = sol.model::Model + function MOI.get( sol::SolFileResults, attr::MOI.ConstraintPrimal, ci::MOI.ConstraintIndex{<:MOI.ScalarAffineFunction}, ) MOI.check_result_index_bounds(sol, attr) - return _evaluate(sol.model.h[ci.value].expr, sol.variable_primal) + return _evaluate(_model(sol).h[ci.value].expr, sol.variable_primal) end function MOI.get( @@ -126,7 +129,7 @@ function MOI.get( ci::MOI.ConstraintIndex{F}, ) where {F<:Union{MOI.ScalarQuadraticFunction,MOI.ScalarNonlinearFunction}} MOI.check_result_index_bounds(sol, attr) - return _evaluate(sol.model.g[ci.value].expr, sol.variable_primal) + return _evaluate(_model(sol).g[ci.value].expr, sol.variable_primal) end function MOI.get( @@ -136,7 +139,7 @@ function MOI.get( ) MOI.check_result_index_bounds(sol, attr) dual = get(sol.zU_out, MOI.VariableIndex(ci.value), 0.0) - return sol.model.sense == MOI.MIN_SENSE ? dual : -dual + return _model(sol).sense == MOI.MIN_SENSE ? dual : -dual end function MOI.get( @@ -146,7 +149,7 @@ function MOI.get( ) MOI.check_result_index_bounds(sol, attr) dual = get(sol.zL_out, MOI.VariableIndex(ci.value), 0.0) - return sol.model.sense == MOI.MIN_SENSE ? dual : -dual + return _model(sol).sense == MOI.MIN_SENSE ? dual : -dual end function MOI.get( @@ -157,7 +160,7 @@ function MOI.get( MOI.check_result_index_bounds(sol, attr) x = MOI.VariableIndex(ci.value) dual = get(sol.zL_out, x, 0.0) + get(sol.zU_out, x, 0.0) - return sol.model.sense == MOI.MIN_SENSE ? dual : -dual + return _model(sol).sense == MOI.MIN_SENSE ? dual : -dual end function MOI.get( @@ -168,7 +171,7 @@ function MOI.get( MOI.check_result_index_bounds(sol, attr) x = MOI.VariableIndex(ci.value) dual = get(sol.zL_out, x, 0.0) + get(sol.zU_out, x, 0.0) - return sol.model.sense == MOI.MIN_SENSE ? dual : -dual + return _model(sol).sense == MOI.MIN_SENSE ? dual : -dual end function MOI.get( @@ -177,8 +180,8 @@ function MOI.get( ci::MOI.ConstraintIndex{<:MOI.ScalarAffineFunction}, ) MOI.check_result_index_bounds(sol, attr) - dual = sol.constraint_dual[length(sol.model.g)+ci.value] - return sol.model.sense == MOI.MIN_SENSE ? dual : -dual + dual = sol.constraint_dual[length(_model(sol).g)+ci.value] + return _model(sol).sense == MOI.MIN_SENSE ? dual : -dual end function MOI.get( @@ -188,13 +191,13 @@ function MOI.get( ) where {F<:Union{MOI.ScalarQuadraticFunction,MOI.ScalarNonlinearFunction}} MOI.check_result_index_bounds(sol, attr) dual = sol.constraint_dual[ci.value] - return sol.model.sense == MOI.MIN_SENSE ? dual : -dual + return _model(sol).sense == MOI.MIN_SENSE ? dual : -dual end function MOI.get(sol::SolFileResults, attr::MOI.NLPBlockDual) MOI.check_result_index_bounds(sol, attr) - dual = sol.constraint_dual[1:sol.model.nlpblock_dim] - return sol.model.sense == MOI.MIN_SENSE ? dual : -dual + dual = sol.constraint_dual[1:_model(sol).nlpblock_dim] + return _model(sol).sense == MOI.MIN_SENSE ? dual : -dual end """ diff --git a/src/Nonlinear/ReverseAD/mathoptinterface_api.jl b/src/Nonlinear/ReverseAD/mathoptinterface_api.jl index e75c07ddec..f7fcd9615d 100644 --- a/src/Nonlinear/ReverseAD/mathoptinterface_api.jl +++ b/src/Nonlinear/ReverseAD/mathoptinterface_api.jl @@ -45,7 +45,7 @@ function MOI.initialize(d::NLPEvaluator, requested_features::Vector{Symbol}) # main_expressions = [c.expression.nodes for (_, c) in d.data.constraints] if d.data.objective !== nothing - pushfirst!(main_expressions, d.data.objective.nodes) + pushfirst!(main_expressions, something(d.data.objective).nodes) end d.subexpression_order, individual_order = _order_subexpressions( main_expressions, @@ -96,9 +96,9 @@ function MOI.initialize(d::NLPEvaluator, requested_features::Vector{Symbol}) end max_chunk = 1 if d.data.objective !== nothing - d.objective = _FunctionStorage( + objective = _FunctionStorage( main_expressions[1], - d.data.objective.values, + something(d.data.objective).values, N, coloring_storage, d.want_hess, @@ -109,8 +109,9 @@ function MOI.initialize(d::NLPEvaluator, requested_features::Vector{Symbol}) subexpression_variables, moi_index_to_consecutive_index, ) - max_expr_length = max(max_expr_length, length(d.objective.nodes)) - max_chunk = max(max_chunk, size(d.objective.seed_matrix, 2)) + max_expr_length = max(max_expr_length, length(objective.nodes)) + max_chunk = max(max_chunk, size(objective.seed_matrix, 2)) + d.objective = objective end for (k, (_, constraint)) in enumerate(d.data.constraints) idx = d.data.objective !== nothing ? k + 1 : k @@ -157,11 +158,9 @@ function MOI.initialize(d::NLPEvaluator, requested_features::Vector{Symbol}) d.max_chunk = max_chunk if d.want_hess d.hessian_sparsity = Tuple{Int64,Int64}[] - if d.objective !== nothing - append!( - d.hessian_sparsity, - zip(d.objective.hess_I, d.objective.hess_J), - ) + obj = d.objective + if obj !== nothing + append!(d.hessian_sparsity, zip(obj.hess_I, obj.hess_J)) end for c in d.constraints append!(d.hessian_sparsity, zip(c.hess_I, c.hess_J)) @@ -277,8 +276,14 @@ end function MOI.hessian_objective_structure(d::NLPEvaluator) @assert d.want_hess + ret = Tuple{Int64,Int64}[] obj = d.objective - return Tuple{Int64,Int64}[(i, j) for (i, j) in zip(obj.hess_I, obj.hess_J)] + if obj !== nothing + for (i, j) in zip(obj.hess_I, obj.hess_J) + push!(ret, (i, j)) + end + end + return ret end function MOI.hessian_constraint_structure(d::NLPEvaluator, c::Integer) diff --git a/src/Nonlinear/evaluator.jl b/src/Nonlinear/evaluator.jl index 2414ac7db1..c8cdc491cf 100644 --- a/src/Nonlinear/evaluator.jl +++ b/src/Nonlinear/evaluator.jl @@ -102,15 +102,16 @@ function MOI.constraint_expr(evaluator::Evaluator, i::Int) constraint.expression; moi_output_format = true, ) - if constraint.set isa MOI.LessThan - return :($f <= $(constraint.set.upper)) - elseif constraint.set isa MOI.GreaterThan - return :($f >= $(constraint.set.lower)) - elseif constraint.set isa MOI.EqualTo - return :($f == $(constraint.set.value)) + set = constraint.set + if set isa MOI.LessThan + return :($f <= $(set.upper)) + elseif set isa MOI.GreaterThan + return :($f >= $(set.lower)) + elseif set isa MOI.EqualTo + return :($f == $(set.value)) else - @assert constraint.set isa MOI.Interval - return :($(constraint.set.lower) <= $f <= $(constraint.set.upper)) + @assert set isa MOI.Interval + return :($(set.lower) <= $f <= $(set.upper)) end end diff --git a/src/Utilities/copy.jl b/src/Utilities/copy.jl index 9af59c7df7..11a76c3ba9 100644 --- a/src/Utilities/copy.jl +++ b/src/Utilities/copy.jl @@ -326,9 +326,9 @@ function _pass_constraints( _copy_constraints(dest, src, index_map, cis) end all_constraint_types = MOI.get(src, MOI.ListOfConstraintTypesPresent()) - nonvariable_constraint_types = Any[ - (F, S) for (F, S) in all_constraint_types if !_is_variable_function(F) - ] + nonvariable_constraint_types = filter(all_constraint_types) do (F, S) + return !_is_variable_function(F) + end pass_nonvariable_constraints( dest, src, diff --git a/src/Utilities/functions.jl b/src/Utilities/functions.jl index 03baca4d20..53fefc8da8 100644 --- a/src/Utilities/functions.jl +++ b/src/Utilities/functions.jl @@ -150,7 +150,7 @@ function eval_variables(value_fn::Function, f::MOI.ScalarQuadraticFunction) end function eval_variables(value_fn::Function, f::MOI.VectorOfVariables) - return value_fn.(f.variables) + return map(value_fn, f.variables) end function eval_variables(value_fn::Function, f::MOI.VectorAffineFunction) @@ -2121,7 +2121,15 @@ vectorize(x::AbstractVector{<:Number}) = x Returns the vector of scalar affine functions in the form of a `MOI.VectorAffineFunction{T}`. """ -vectorize(x::AbstractVector{MOI.VariableIndex}) = MOI.VectorOfVariables(x) +function vectorize(x::AbstractVector{MOI.VariableIndex}) + # Explicitly construct the output vector here because don't know that `x` + # has a `convert` method to `Vector`. + y = Vector{MOI.VariableIndex}(undef, length(x)) + for (i, xi) in enumerate(x) + y[i] = xi + end + return MOI.VectorOfVariables(y) +end """ vectorize(funcs::AbstractVector{MOI.ScalarAffineFunction{T}}) where T @@ -2175,7 +2183,13 @@ function vectorize( end function vectorize(x::AbstractVector{MOI.ScalarNonlinearFunction}) - return MOI.VectorNonlinearFunction(x) + # Explicitly construct the output vector here because don't know that `x` + # has a `convert` method to `Vector`. + y = Vector{MOI.ScalarNonlinearFunction}(undef, length(x)) + for (i, xi) in enumerate(x) + y[i] = xi + end + return MOI.VectorNonlinearFunction(y) end scalarize(f::AbstractVector, ::Bool = false) = f diff --git a/src/Utilities/matrix_of_constraints.jl b/src/Utilities/matrix_of_constraints.jl index 10bdac499f..843f2262cc 100644 --- a/src/Utilities/matrix_of_constraints.jl +++ b/src/Utilities/matrix_of_constraints.jl @@ -271,7 +271,7 @@ function rows end MOI.is_empty(v::MatrixOfConstraints) = MOI.is_empty(v.sets) -function MOI.empty!(v::MatrixOfConstraints{T}) where {T} +function MOI.empty!(v::MatrixOfConstraints{T,AT,BT,ST}) where {T,AT,BT,ST} MOI.empty!(v.coefficients) empty!(v.constants) MOI.empty!(v.sets) diff --git a/src/Utilities/model.jl b/src/Utilities/model.jl index b385b9d376..c29c4b1278 100644 --- a/src/Utilities/model.jl +++ b/src/Utilities/model.jl @@ -34,10 +34,6 @@ function MOI.add_variable(model::AbstractModel) return x end -function MOI.add_variables(model::AbstractModel, n::Integer) - return [MOI.add_variable(model) for i in 1:n] -end - """ remove_variable(f::MOI.AbstractFunction, s::MOI.AbstractSet, vi::MOI.VariableIndex) diff --git a/src/Utilities/objective_container.jl b/src/Utilities/objective_container.jl index 30fa031c52..59f046d8a0 100644 --- a/src/Utilities/objective_container.jl +++ b/src/Utilities/objective_container.jl @@ -118,8 +118,20 @@ end function MOI.get( o::ObjectiveContainer{T}, - ::MOI.ObjectiveFunction{F}, -) where {T,F} + attr::MOI.ObjectiveFunction{F}, +) where { + T, + F<:Union{ + MOI.VariableIndex, + MOI.ScalarAffineFunction, + MOI.ScalarQuadraticFunction, + MOI.ScalarNonlinearFunction, + MOI.VectorOfVariables, + MOI.VectorAffineFunction, + MOI.VectorQuadraticFunction, + MOI.VectorNonlinearFunction, + }, +} if o.scalar_affine !== nothing return convert(F, something(o.scalar_affine)) elseif o.single_variable !== nothing diff --git a/src/Utilities/parser.jl b/src/Utilities/parser.jl index 01e942cd8d..8b030be9ce 100644 --- a/src/Utilities/parser.jl +++ b/src/Utilities/parser.jl @@ -60,10 +60,10 @@ function _parse_function(ex, ::Type{T} = Float64) where {T} if isa(ex, Symbol) return _ParsedVariableIndex(ex) elseif Meta.isexpr(ex, :vect) - if all(s -> isa(s, Symbol), ex.args) + if all(Base.Fix2(isa, Symbol), ex.args) return _ParsedVectorOfVariables(copy(ex.args)) else - singlefunctions = _parse_function.(ex.args, T) + singlefunctions = map(Base.Fix2(_parse_function, T), ex.args) affine_terms = _ParsedVectorAffineTerm{T}[] quadratic_terms = _ParsedVectorQuadraticTerm{T}[] constant = T[] diff --git a/src/Utilities/print.jl b/src/Utilities/print.jl index 41d3e747bc..0c282d17eb 100644 --- a/src/Utilities/print.jl +++ b/src/Utilities/print.jl @@ -113,10 +113,10 @@ function _to_string( var_name = replace(var_name, "^" => "\\^") # Convert any x[args] to x_{args} so that indices on x print as subscripts. m = match(r"^(.*)\[(.+)\]$", var_name) - if m !== nothing - var_name = m[1] * "_{" * m[2] * "}" + if m === nothing + return var_name end - return var_name + return string(m[1]::AbstractString, "_{", m[2]::AbstractString, "}") end function _shorten(options::_PrintOptions, x::Float64) diff --git a/src/Utilities/product_of_sets.jl b/src/Utilities/product_of_sets.jl index cc2973e82d..cc7ac78512 100644 --- a/src/Utilities/product_of_sets.jl +++ b/src/Utilities/product_of_sets.jl @@ -219,7 +219,7 @@ function rows( ci::MOI.ConstraintIndex{MOI.ScalarAffineFunction{T},S}, ) where {T,S} @assert sets.final_touch - i = set_index(sets, S) + i = set_index(sets, S)::Int return (i == 1 ? 0 : sets.num_rows[i-1]) + ci.value end @@ -228,7 +228,7 @@ function rows( ci::MOI.ConstraintIndex{MOI.VectorAffineFunction{T},S}, ) where {T,S} @assert sets.final_touch - i = set_index(sets, S) + i = set_index(sets, S)::Int offset = i == 1 ? 0 : sets.num_rows[i-1] return (offset + ci.value - 1) .+ (1:sets.dimension[(i, ci.value)]) end @@ -263,7 +263,7 @@ Return the number of rows corresponding to a set of type `S`. That is, it is the sum of the dimensions of the sets of type `S`. """ function num_rows(sets::OrderedProductOfSets, ::Type{S}) where {S} - i = set_index(sets, S) + i = set_index(sets, S)::Int if !sets.final_touch || i == 1 return sets.num_rows[i] end diff --git a/src/Utilities/struct_of_constraints.jl b/src/Utilities/struct_of_constraints.jl index 41d6f83cda..b383ceeb5c 100644 --- a/src/Utilities/struct_of_constraints.jl +++ b/src/Utilities/struct_of_constraints.jl @@ -283,7 +283,7 @@ function struct_of_constraint_code(struct_name, types, field_types = nothing) typed_struct = :($(struct_name){$T}) type_parametrized = field_types === nothing if type_parametrized - field_types = [Symbol("C$i") for i in eachindex(types)] + field_types = Symbol[Symbol("C$i") for i in eachindex(types)] append!(typed_struct.args, field_types) end code = quote diff --git a/src/Utilities/universalfallback.jl b/src/Utilities/universalfallback.jl index db1e624867..0c90656c41 100644 --- a/src/Utilities/universalfallback.jl +++ b/src/Utilities/universalfallback.jl @@ -579,7 +579,7 @@ function MOI.modify( if uf.objective === nothing MOI.modify(uf.model, obj, change) else - uf.objective = modify_function(uf.objective, change) + uf.objective = modify_function(something(uf.objective), change) end return end diff --git a/src/Utilities/vector_of_constraints.jl b/src/Utilities/vector_of_constraints.jl index 886447edd5..6033121118 100644 --- a/src/Utilities/vector_of_constraints.jl +++ b/src/Utilities/vector_of_constraints.jl @@ -102,7 +102,8 @@ function MOI.get( ci::MOI.ConstraintIndex{F,S}, ) where {F,S} MOI.throw_if_not_valid(v, ci) - return v.constraints[ci][1] + f, _ = v.constraints[ci]::Tuple{F,S} + return f end function MOI.get( @@ -111,7 +112,8 @@ function MOI.get( ci::MOI.ConstraintIndex{F,S}, ) where {F,S} MOI.throw_if_not_valid(v, ci) - return v.constraints[ci][2] + _, s = v.constraints[ci]::Tuple{F,S} + return s end function MOI.set( @@ -121,7 +123,8 @@ function MOI.set( func::F, ) where {F,S} MOI.throw_if_not_valid(v, ci) - v.constraints[ci] = (func, v.constraints[ci][2]) + _, s = v.constraints[ci]::Tuple{F,S} + v.constraints[ci] = (func, s) return end @@ -132,7 +135,8 @@ function MOI.set( set::S, ) where {F,S} MOI.throw_if_not_valid(v, ci) - v.constraints[ci] = (v.constraints[ci][1], set) + f, _ = v.constraints[ci]::Tuple{F,S} + v.constraints[ci] = (f, set) return end @@ -162,7 +166,7 @@ function MOI.modify( ci::MOI.ConstraintIndex{F,S}, change::MOI.AbstractFunctionModification, ) where {F,S} - func, set = v.constraints[ci] + func, set = v.constraints[ci]::Tuple{F,S} v.constraints[ci] = (modify_function!(func, change), set) return end diff --git a/src/functions.jl b/src/functions.jl index a99c4a3fa4..b2e1ce05ce 100644 --- a/src/functions.jl +++ b/src/functions.jl @@ -549,7 +549,8 @@ function VectorAffineFunction{T}(f::VectorOfVariables) where {T} terms = map(1:output_dimension(f)) do i return VectorAffineTerm(i, ScalarAffineTerm(one(T), f.variables[i])) end - return VectorAffineFunction(terms, zeros(T, output_dimension(f))) + constants = zeros(T, output_dimension(f))::Vector{T} + return VectorAffineFunction(terms, constants) end """