Variance: private API
PortfolioOptimisers.NSkeQuadFormulations — Type
const NSkeQuadFormulationsUnion of the second-moment formulations that state the risk of the Negative Skewness risk measure as an explicit square.
Specifically: Union{<:QuadRiskExpr, <:SquaredSOCRiskExpr}.
Related
PortfolioOptimisers.QuadSecondMomentFormulations — Type
const QuadSecondMomentFormulations = Union{<:NSkeQuadFormulations, <:RSOCRiskExpr}Union of the second-moment formulations that report the second moment itself rather than its square root.
Related
PortfolioOptimisers.SecondMomentFormulation — Type
abstract type SecondMomentFormulation <: AbstractAlgorithmAbstract supertype for the JuMP encodings of a second moment.
A second-moment risk measure hands the formulation a deviation vector and a correction factor, and the formulation decides which quadratic object or cone carries the sum of squares. The four encodings differ in the cone they need and in the units they report: SOCRiskExpr reports the square root of the second moment, and the other three report the second moment itself. A bound in settings.ub is stated in the units that the chosen formulation reports. The cone encodings bound the sum of squares from above, so they are tight where the risk is minimised or bounded above, which is how a risk expression enters the model.
All concrete types implementing a second-moment JuMP encoding should subtype SecondMomentFormulation.
Related
PortfolioOptimisers.VarianceFormulation — Type
abstract type VarianceFormulation <: SecondMomentFormulationAbstract supertype for the second-moment encodings that state the risk as an explicit square.
Variance accepts these two and no others. Both report the variance itself, one as a quadratic form in the weights and the other as the square of a second-order cone variable.
Related
PortfolioOptimisers.resolve_deferred_quantities — Method
resolve_deferred_quantities(x, ) -> StandardDeviation
resolve_deferred_quantities(x, , ) -> StandardDeviation
Resolve every Deferred Quantity held by x against prior result pr, returning a struct of the same type whose deferred slots hold plain values.
This resolves the deferred state and nothing else. A slot left unstated stays nothing, so whichever fallback the consumer already applies — sel on the factory path, chol_sigma_selector and its siblings on the JuMP path — keeps working unchanged. The two paths are separate: a JuMP model builder reads the risk measure's slots directly and never calls factory, so both entry points resolve.
Given a prior result the rule has two halves. Container recursion is derived from deferred_slots, so a type that only holds children needs no method at all. A type that resolves a quantity of its own defines a method, which overrides the derived one. Writing that half per type — rather than per field — is what lets slots that travel together be resolved together: a deferred sigma supplies chol from the same fit, so the pair is never mixed across two sources.
slv is the effective solver, and it is what a Calibration Rule in the same struct reads. It carries the value the optimisation settled on, so a rule resolves against one solver on both routes. On the factory route the @cprop selection has already put that solver on the struct, so the argument stays at its default. On the JuMP route no selection runs, so set_risk_constraints! reads the solver off the estimator and threads it here. A type that carries a solver of its own settles it locally as sel(x.slv, slv), beside the observation weights it already settles that way, and a type that carries none gives its rules none on either route.
Algorithm
- Return
xunchanged. This method is the arm for a second argument that is not a prior result: with no prior in hand nothing can be fitted, so the deferred state travels on.
A more specific method dominates this one on a prior result: the one that deferred_slots derives for a container, and the hand-written one of a type that resolves a quantity of its own.
Related
resolve_deferred_quantities(x, pr::AbstractPriorResult, slv = nothing)Resolve the children that deferred_slots declared and the slots that calibration_slots declared, and return x itself when none of them changed.
This is the derived half of the resolution rule. A container declares its children once and both entry points follow: factory reaches them through @fprop, and the JuMP builders reach them through this method. Neither needs a forwarding method per container.
A type that resolves a quantity of its own overrides this with its own method, which is more specific. So the derivation carries container recursion alone, and never guesses how a matrix, a tensor or the centre a moment was taken about comes out of a fit.
Both channels end in one rebuild: a measure that carries both kinds of slot must not be rebuilt twice. resolve_calibration_slots states the calibration half and returns its resolved slots rather than a rebuilt object, and the two answers merge here. The deferred half merges last, so it wins a key both channels declare. A container names one child in both, and the child the recursion resolved is the one to keep.
slv is the effective solver, and the recursion threads it to every child. A container states no solver of its own, so it changes none: each child settles the one it was handed against the one it carries.
Algorithm
- Read the slots
xdeclares withdeferred_slots, givingslots. - Read the resolved calibration slots with
resolve_calibration_slots, givingcalibrated. - Return
xunchanged when both are empty. A type with neither kind of slot needs no method of its own. - Resolve every entry of
slotswithresolve_deferred_child, threadingprandslvto each, givingresolved. - Refuse a slot the recursion left unresolved with
assert_declared_slot_resolver. - Hand
merge(calibrated, resolved)torebuild_with_slots, which returnsxitself when no entry moved and a rebuilt copy when one did.
Returns
xitself when no slot moved, and a rebuilt copy ofxwhen one did.
Related
resolve_deferred_quantities(
r::Variance,
pr::AbstractPriorResult
) -> Variance
resolve_deferred_quantities(
r::Variance,
pr::AbstractPriorResult,
) -> Variance
Resolve a Deferred Quantity in Variance's sigma slot against prior result pr.
sigma and chol travel together, so both come from the same fit. A stated chol never reaches here: assert_derived_slot_has_source refuses it beside a deferred sigma at construction. A covariance estimator produces no factorisation, so chol becomes nothing and the consumer derives it from the resolved sigma. A prior estimator produces both, which is how a factor prior's sparse factorisation reaches the slot intact.
Related
PortfolioOptimisers.resolve_deferred_quantities — Method
resolve_deferred_quantities(x, ) -> StandardDeviation
resolve_deferred_quantities(x, , ) -> StandardDeviation
Resolve every Deferred Quantity held by x against prior result pr, returning a struct of the same type whose deferred slots hold plain values.
This resolves the deferred state and nothing else. A slot left unstated stays nothing, so whichever fallback the consumer already applies — sel on the factory path, chol_sigma_selector and its siblings on the JuMP path — keeps working unchanged. The two paths are separate: a JuMP model builder reads the risk measure's slots directly and never calls factory, so both entry points resolve.
Given a prior result the rule has two halves. Container recursion is derived from deferred_slots, so a type that only holds children needs no method at all. A type that resolves a quantity of its own defines a method, which overrides the derived one. Writing that half per type — rather than per field — is what lets slots that travel together be resolved together: a deferred sigma supplies chol from the same fit, so the pair is never mixed across two sources.
slv is the effective solver, and it is what a Calibration Rule in the same struct reads. It carries the value the optimisation settled on, so a rule resolves against one solver on both routes. On the factory route the @cprop selection has already put that solver on the struct, so the argument stays at its default. On the JuMP route no selection runs, so set_risk_constraints! reads the solver off the estimator and threads it here. A type that carries a solver of its own settles it locally as sel(x.slv, slv), beside the observation weights it already settles that way, and a type that carries none gives its rules none on either route.
Algorithm
- Return
xunchanged. This method is the arm for a second argument that is not a prior result: with no prior in hand nothing can be fitted, so the deferred state travels on.
A more specific method dominates this one on a prior result: the one that deferred_slots derives for a container, and the hand-written one of a type that resolves a quantity of its own.
Related
resolve_deferred_quantities(x, pr::AbstractPriorResult, slv = nothing)Resolve the children that deferred_slots declared and the slots that calibration_slots declared, and return x itself when none of them changed.
This is the derived half of the resolution rule. A container declares its children once and both entry points follow: factory reaches them through @fprop, and the JuMP builders reach them through this method. Neither needs a forwarding method per container.
A type that resolves a quantity of its own overrides this with its own method, which is more specific. So the derivation carries container recursion alone, and never guesses how a matrix, a tensor or the centre a moment was taken about comes out of a fit.
Both channels end in one rebuild: a measure that carries both kinds of slot must not be rebuilt twice. resolve_calibration_slots states the calibration half and returns its resolved slots rather than a rebuilt object, and the two answers merge here. The deferred half merges last, so it wins a key both channels declare. A container names one child in both, and the child the recursion resolved is the one to keep.
slv is the effective solver, and the recursion threads it to every child. A container states no solver of its own, so it changes none: each child settles the one it was handed against the one it carries.
Algorithm
- Read the slots
xdeclares withdeferred_slots, givingslots. - Read the resolved calibration slots with
resolve_calibration_slots, givingcalibrated. - Return
xunchanged when both are empty. A type with neither kind of slot needs no method of its own. - Resolve every entry of
slotswithresolve_deferred_child, threadingprandslvto each, givingresolved. - Refuse a slot the recursion left unresolved with
assert_declared_slot_resolver. - Hand
merge(calibrated, resolved)torebuild_with_slots, which returnsxitself when no entry moved and a rebuilt copy when one did.
Returns
xitself when no slot moved, and a rebuilt copy ofxwhen one did.
Related
resolve_deferred_quantities(
r::StandardDeviation,
pr::AbstractPriorResult
) -> StandardDeviation
resolve_deferred_quantities(
r::StandardDeviation,
pr::AbstractPriorResult,
) -> StandardDeviation
Resolve a Deferred Quantity in StandardDeviation's sigma slot against prior result pr. sigma and chol come from the same fit — see resolve_deferred_quantities(r::Variance, pr::AbstractPriorResult).
Related
PortfolioOptimisers.resolve_deferred_quantities — Method
resolve_deferred_quantities(x, ) -> StandardDeviation
resolve_deferred_quantities(x, , ) -> StandardDeviation
Resolve every Deferred Quantity held by x against prior result pr, returning a struct of the same type whose deferred slots hold plain values.
This resolves the deferred state and nothing else. A slot left unstated stays nothing, so whichever fallback the consumer already applies — sel on the factory path, chol_sigma_selector and its siblings on the JuMP path — keeps working unchanged. The two paths are separate: a JuMP model builder reads the risk measure's slots directly and never calls factory, so both entry points resolve.
Given a prior result the rule has two halves. Container recursion is derived from deferred_slots, so a type that only holds children needs no method at all. A type that resolves a quantity of its own defines a method, which overrides the derived one. Writing that half per type — rather than per field — is what lets slots that travel together be resolved together: a deferred sigma supplies chol from the same fit, so the pair is never mixed across two sources.
slv is the effective solver, and it is what a Calibration Rule in the same struct reads. It carries the value the optimisation settled on, so a rule resolves against one solver on both routes. On the factory route the @cprop selection has already put that solver on the struct, so the argument stays at its default. On the JuMP route no selection runs, so set_risk_constraints! reads the solver off the estimator and threads it here. A type that carries a solver of its own settles it locally as sel(x.slv, slv), beside the observation weights it already settles that way, and a type that carries none gives its rules none on either route.
Algorithm
- Return
xunchanged. This method is the arm for a second argument that is not a prior result: with no prior in hand nothing can be fitted, so the deferred state travels on.
A more specific method dominates this one on a prior result: the one that deferred_slots derives for a container, and the hand-written one of a type that resolves a quantity of its own.
Related
resolve_deferred_quantities(x, pr::AbstractPriorResult, slv = nothing)Resolve the children that deferred_slots declared and the slots that calibration_slots declared, and return x itself when none of them changed.
This is the derived half of the resolution rule. A container declares its children once and both entry points follow: factory reaches them through @fprop, and the JuMP builders reach them through this method. Neither needs a forwarding method per container.
A type that resolves a quantity of its own overrides this with its own method, which is more specific. So the derivation carries container recursion alone, and never guesses how a matrix, a tensor or the centre a moment was taken about comes out of a fit.
Both channels end in one rebuild: a measure that carries both kinds of slot must not be rebuilt twice. resolve_calibration_slots states the calibration half and returns its resolved slots rather than a rebuilt object, and the two answers merge here. The deferred half merges last, so it wins a key both channels declare. A container names one child in both, and the child the recursion resolved is the one to keep.
slv is the effective solver, and the recursion threads it to every child. A container states no solver of its own, so it changes none: each child settles the one it was handed against the one it carries.
Algorithm
- Read the slots
xdeclares withdeferred_slots, givingslots. - Read the resolved calibration slots with
resolve_calibration_slots, givingcalibrated. - Return
xunchanged when both are empty. A type with neither kind of slot needs no method of its own. - Resolve every entry of
slotswithresolve_deferred_child, threadingprandslvto each, givingresolved. - Refuse a slot the recursion left unresolved with
assert_declared_slot_resolver. - Hand
merge(calibrated, resolved)torebuild_with_slots, which returnsxitself when no entry moved and a rebuilt copy when one did.
Returns
xitself when no slot moved, and a rebuilt copy ofxwhen one did.
Related
resolve_deferred_quantities(
r::UncertaintySetVariance,
pr::AbstractPriorResult
) -> UncertaintySetVariance
resolve_deferred_quantities(
r::UncertaintySetVariance,
pr::AbstractPriorResult,
) -> UncertaintySetVariance
Resolve a Deferred Quantity in UncertaintySetVariance's sigma slot against prior result pr. The measure carries one prior-derived slot, so the slot itself admits the estimator and there is no fan-out to make.
Related
PortfolioOptimisers._no_bounds_risk_measure — Method
_no_bounds_risk_measure(r, flag)Return a version of the risk measure stripped of bounds for unbounded optimisation sub-problems.
Internal helper used in frontier construction sub-problems where bounds are temporarily removed.
Arguments
r: Risk measure.flag: Flag controlling which bounds to remove.
Returns
- Risk measure without bounds.
Related
PortfolioOptimisers._no_bounds_no_risk_expr_risk_measure — Method
_no_bounds_no_risk_expr_risk_measure(r, flag)Return a version of the risk measure with neither bounds nor risk expressions for unbounded sub-problems.
Internal helper used in frontier sub-problems that require removing all risk expression constraints.
Arguments
r: Risk measure.flag: Flag controlling configuration.
Returns
- Simplified risk measure.
Related
PortfolioOptimisers.ucs_risk_measure — Function
ucs_risk_measure(r, rd::ReturnsResult)Resolve the uncertainty set of an UncertaintySetVariance risk measure to a fitted AbstractUncertaintySetResult using the returns data. Other risk measures are returned unchanged; vectors of risk measures are resolved element-wise.
A risk measure whose slot holds an estimator that reads a prior result — one for which reads_prior_result answers true: an AbstractPriorUncertaintySetEstimator, or a returns-data estimator with pe = nothing — is returned unchanged too. Such an estimator is calibrated on the optimisation's own prior result, and this pre-fit runs before any prior exists, so the estimator travels to the builder and each corner solve fits it there against the prior that solve was handed.
Used by near_optimal_centering_setup so that the barrier risk targets, the sub-problem solves, and the NOC model all share the same fitted uncertainty set (fitted results pass through sigma_ucs unchanged). With a fitted set the UncertaintySetVariance functor evaluates the worst-case variance via ucs_variance, keeping the barrier targets consistent with the model risk expression.
Related
PortfolioOptimisers.ucs_variance — Function
ucs_variance(ucs::AbstractUncertaintySetResult, sigma::MatNum, w::VecNum)Compute the worst-case portfolio variance of weights w over a fitted uncertainty set.
This is the scalar twin of the JuMP expression built by set_ucs_variance_risk!: for a BoxUncertaintySet it evaluates tr(Au * ub) - tr(Al * lb) at the optimal Au = max.(W, 0), Al = max.(-W, 0) with W = w * w'; for an EllipsoidalUncertaintySet it evaluates tr(sigma * W) + k * norm(G * vec(W)) with G the upper Cholesky factor of the set's shape matrix (the E = 0 evaluation of the model expression, an upper bound on its optimum); for a CompactCovarianceUncertaintySet it evaluates w' * sigma * w plus kappa times the squared norm of the least-squares residual of C .* w against the set's basis. The compact evaluation solves the same inner problem the model variable z_cucs solves, so it is that expression's optimum and not a bound on it. For a covariance NormBallUncertaintySet it evaluates tr(sigma * W) + kappa * norm(L' * vec(W), q) with q the dual norm order of the set (again the E = 0 evaluation, an upper bound on the model expression's optimum), and a map with no column pays nothing.
The UncertaintySetVariance functor dispatches here when its ucs field is a fitted result, keeping scalar risk evaluation consistent with the risk expression the optimiser sees.
Arguments
ucs: Fitted uncertainty set result.sigma::MatNum: Fallback covariance matrix. The set's ownvalfield wins over it.w::VecNum: Vector of portfolio weights.
Returns
risk::Number: Worst-case portfolio variance.
Related