Mean-Variance Portfolio Optimization with Long-Only Constraints
Summary
The document explains how to formulate a mean-variance portfolio problem for a quadratic programming solver. To maximize expected return minus a risk penalty based on covariance, the objective must be converted to the solver’s minimization form: use a covariance matrix scaled to match the quadratic convention and negate the expected-return vector. The risk-aversion parameter controls the trade-off between return and variance.
The example uses linear constraints to require nonnegative weights and, in a second version, to make weights sum to one. It shows a sample result in which the asset with negative expected return receives zero weight. The example uses simulated returns and does not compare risk-aversion settings or establish out-of-sample performance. Its initial constraints allow weights above one; a separate upper bound is needed if individual weights must be capped. The discussion also does not resolve details of the original loop’s dimensions or how its different covariance matrices and expected returns are constructed.
Key ideas
- Quadratic programming can express mean-variance allocation by minimizing a risk quadratic adjusted for expected return.
- The covariance matrix and return vector must be signed and scaled to match the solver’s objective convention.
- Nonnegative weight constraints exclude short positions.
- A separate equality constraint makes portfolio weights sum to one.
- Upper bounds on individual weights require additional constraints.
Tags
Full text
# Portfolio Optmization With Risk Aversion Parameter R
# Portfolio Optmization With Risk Aversion Parameter R
I have this problem in R.
$$\max w^Tu- y w^T A w$$ where A is covariance variance matrix, y risk aversion parameter. Is it rigth if I use the function solve.QP multiplying the covariance matrix for lambda and setting dvec (vector appearing in the quadratic function to be minimized) equal to the vector of mean returns of the asset? In order to find the maximum I have to change the sign
```
weigth4<- matrix(0, nrow=15, ncol=15)
mu <- matrix(NA, nrow=15, ncol=15)
for ( i in 1:15){
mu[i,]<- mean(c[[i]][2])
}
Amat<- cbind(1, diag(15), -diag(15))
bvec<- c(1, rep(0.01, 15), rep(-0.5,15))
for ( i in 1:15){
result4<- solve.QP(Dmat=2*list[[i]], dvec=(-1)*mu[1,], Amat=Amat, bvec=bvec, meq=1)
weigth4[i,]<- result4$solution
}
```
In the case of expected utility maximization, I also want to check for the impact of different values of y= 0, 1, 5, 10. In any event, please rule out any short positions. How can I find these portfolios?
## Answer by Richi Wa (score 2)
https://quant.stackexchange.com/a/39318
You can look at the example here.
I adapted is a bit. Below first I sample returns of stocks with 20% vola pa. Then I calculate the covariance matrix. In the quadprog-part I define the matirx `Amat` as diagonal and `bvec` as zeros. Then $$ Amat * w \ge bvec $$ gives you the non-negative weight constraint. You can play around and find the constraint for the weights summing up to 1.
In the solution blow you see that the stock with the negative expected mean was not chosen and all weights are non-negative.
```
library(quadprog)
rets = rnorm(20*3,mean=0, sd = 0.2/sqrt(250))
matrix(rets, ncol=3)
Dmat <- cov(matrix(rets, ncol=3))
dvec <- c(0.01,0.01,-0.01)
Amat <- diag(3)
bvec <- c(0,0,0)
solve.QP(Dmat,dvec,Amat,bvec=bvec)
```
> `$solution [1] 34.39526 60.13777 0.00000 > > $value [1] -0.4726651 $unconstrained.solution [1] -5.189056 100.950539 -146.724093 > > $iterations [1] 2 0 $Lagrangian [1] 0.00000000 0.00000000 0.01008373 > > $iact [1] 3 `
```
$solution [1] 34.39526 60.13777 0.00000
>
> $value [1] -0.4726651
$unconstrained.solution [1] -5.189056 100.950539 -146.724093
>
> $iterations [1] 2 0
$Lagrangian [1] 0.00000000 0.00000000 0.01008373
>
> $iact [1] 3
```
Ok, the code below gives you the portfolios constraint as well:
```
Dmat <- cov(matrix(rets, ncol=3))
dvec <- c(0.01,0.01,-0.01)
Amat <- diag(3)
Amat = cbind( c(1,1,1), Amat)
bvec <- c(0,0,0)
bvec = c(1,bvec)
solve.QP(Dmat,dvec,Amat,bvec=bvec, meq = 1)
```
> `$solution > [1] 0.3638438 0.6361562 0.0000000 > > $value [1] -0.009947108 $unconstrained.solution > [1] -5.189056 100.950539 -146.724093 > > $iterations [1] 3 0 $Lagrangian > [1] 0.009894217 0.000000000 0.000000000 0.019895103 > > $iact [1] 4 1 `
```
$solution
> [1] 0.3638438 0.6361562 0.0000000
>
> $value
[1] -0.009947108
$unconstrained.solution
> [1] -5.189056 100.950539 -146.724093
>
> $iterations
[1] 3 0
$Lagrangian
> [1] 0.009894217 0.000000000 0.000000000 0.019895103
>
> $iact
[1] 4 1
```
You need the `meq` with tell the quadprog that the first constraint is equality. Then you translate the $w_1 + w_2 + w_3 = 1$ in the `Amat` and `bvec` setting.Shown in full with attribution under the source's licence. Licence: CC BY-SA 4.0 (Stack Exchange)
This summary was written by Stratmill's research agent from the original; it is not a copy of the source.