EfficientFrontier
Documentation for EfficientFrontier.
EfficientFrontier.EfficientFrontier
EfficientFrontier.Event
EfficientFrontier.Problem
EfficientFrontier.Settings
EfficientFrontier.Status
EfficientFrontier.sCL
EfficientFrontier.sEF
EfficientFrontier.ECL
EfficientFrontier.ECL!
EfficientFrontier.cbCL!
EfficientFrontier.computeCL!
EfficientFrontier.eFrontier
EfficientFrontier.ePortfolio
EfficientFrontier.EfficientFrontier
— ModuleFull Efficient Frontier by connecting Critical Line Segments
EfficientFrontier.Event
— Type struct Event{T<:AbstractFloat}
Events that assets go IN/OUT(DN or UP), or inequalities go binded (EO, as equality) or not (OE, original ineq), with fields:
From::Status
To::Status
id::Int
L::T
EfficientFrontier.Problem
— Type Problem(E, V; u, d, G, g, A, b, equilibrate)
Problem(E, V, u; equilibrate)
Problem(E, V, u, d; equilibrate)
Problem(E, V, u, d, G, g; equilibrate)
Problem(E, V, u, d, G, g, A, b; equilibrate)
Setup a Portfolio Selection model: for mean vector E and variance matrix V
\[ min (1/2)z′Vz s.t. z′E = μ Az = b ∈ R^{M} Gz ≤ g ∈ R^{J} d ≤ z ≤ u ∈ R^{N}\]
Default values: u = +∞, d = 0, G = [], g = [], A = ones(1,N), b = [1], and equilibrate = false
Example
using EfficientFrontier
V = [1/100 1/80 1/100
1/80 1/16 1/40
1/100 1/40 1/25] #variance matrix
E = [109 / 100; 23 / 20; 119 / 100] #mean vector
P = Problem(E, V) #Default models, non-shortsale
aCL = EfficientFrontier.ECL(P) #compute all Critical Lines
aEF = eFrontier(aCL, P) #compute the Efficient Frontier
mu = (aEF.mu[1]+aEF.mu[end])/2 #mu at the middle of Efficient Frontier
z = ePortfolio(mu, aEF) #weight of the efficient portfolio given mu
See Documentation for EfficientFrontier.jl
See also EfficientFrontier.ECL
EfficientFrontier.Settings
— Type Settings(P::Problem) The default Settings to given Problem
Settings(; kwargs...) The default Settings is set by Float64 type
Settings{T<:AbstractFloat}(; kwargs...)
kwargs are from the fields of Settings{T<:AbstractFloat} for Float64 and BigFloat
tol::T #general scalar
tolNorm::T #for norms
tolS::T #for s from Clarabel
tolL::T #for L
tolG::T #for Greeks (beta and gamma)
muShft::T #shift the max mu to (1-muShft)*mu
EfficientFrontier.Status
— Type @enum Status
Status: assets go IN/OUT(DN or UP), or inequalities go binded (EO, as equality) or not (OE, original ineq), with fields:
IN #within the lower and upper bound
DN #down, lower bound
UP #upper bound
OE #original <= not binded
EO #edge, <= as =
EfficientFrontier.sCL
— Type struct sCL{T<:AbstractFloat}
Critical Line segment, with fields: default T = Float64
S::Vector{Status} # (N+J)x1
K::Integer #number of IN assets
L1::T #higher lambda
I1::Vector{Event{T}} #go in/out events at L1
L0::T #lower lambda
I0::Vector{Event{T}} #go in/out events at L0
alpha::Vector{T} # K x 1
beta::Vector{T} # K x 1
EfficientFrontier.sEF
— Type struct sEF
Efficient Frontier, with fields:
Ap::Matrix{Float64} # v=a₂μ²+a₁μ+a₀, each row [a₂ a₁ a₀]
mu::Vector{Float64} #higher mean
sgm::Vector{Float64} #higher sigma
Z::Matrix{Float64} #weights, each corner portfolio in one row
ic::Vector{Int64} #id of related critical line
EfficientFrontier.ECL!
— Method ECL!(aCL::Vector{sCL{T}}, PS::Problem{T}; numSettings = Settings(PS), incL=false) where T
compute all the Critical Line Segments as L decreasing to 0 (increasing to +Inf if incL=true), given the first one in aCL[end]. Return value: true if done
EfficientFrontier.ECL
— Method aCL = ECL(PS::Problem; numSettings = Settings(PS), init::Function=cbCL!)
compute all the Critical Line Segments. Init the CL by combinatorial search
the return aCL has the follwing structure
struct sCL{T<:AbstractFloat} #critical line segment
S::Vector{Status} # (N+J)x1
K::Integer #number of IN assets
L1::T #higher lambda
I1::Vector{Event{T}} #go in/out events at L1
L0::T #lower lambda
I0::Vector{Event{T}} #go in/out events at L0
alpha::Vector{T} # K x 1
beta::Vector{T} # K x 1
end
See https://github.com/PharosAbad/EfficientFrontier.jl/wiki
EfficientFrontier.cbCL!
— Method cbCL!(aCL::Vector{sCL{T}}, PS::Problem{T}; nS=Settings(PS), oneCL=true, K=PS.M+PS.J+1) where T
compute one or all (oneCL=false, K=PS.M) the Critical Line Segments by enumerating (combinations of Status)
EfficientFrontier.computeCL!
— Method computeCL!(aCL::Vector{sCL{T}}, S::Vector{Status}, PS::Problem{T}, nS::Settings{T}) where T
compute the Critical Line Segment for S::Vector{Status}, save to aCL[end]. Return value: true if done.
EfficientFrontier.eFrontier
— Method aEF = eFrontier(aCL::Vector{sCL{T}}, PS::Problem{T}; tolNorm = 2^-26) where T
compute the Full Efficient Frontier by connecting Critical Line Segments
the return aEF has the follwing structure
struct sEF #Efficient Frontier Float64 is OK
Ap::Matrix{Float64} # v=a₂μ²+a₁μ+a₀, each row [a₂ a₁ a₀]
mu::Vector{Float64} #higher mean
sgm::Vector{Float64} #higher sigma
Z::Matrix{Float64} #weights, each corner portfolio in one row
ic::Vector{Int64} #id of related critical line
end
EfficientFrontier.ePortfolio
— Method z = ePortfolio(mu, aEF::sEF)
compute the efficient portfolio given mu, returns portfolio weights z (Nx1 vector of NaN if mu is out of range)