# Differences

This shows you the differences between two versions of the page.

Both sides previous revision Previous revision Next revision | Previous revision | ||

personal:portfolio:portopt [2014/05/28 09:21] antonello |
personal:portfolio:portopt [2016/02/15 11:19] antonello |
||
---|---|---|---|

Line 1: | Line 1: | ||

- | PortOpt [Portfolio Optimizer] is a C++ program (with Python binding) implementing the Markowitz(1952) [[http://en.wikipedia.org/wiki/Modern_portfolio_theory|mean-variance model]] with agent's linear indifference curves toward risk in order to find the optimal assets portfolio under risk. | + | PortOpt [Portfolio Optimizer] is an open-source (LGPLed) C++ program (with Python binding) implementing the Markowitz(1952) [[http://en.wikipedia.org/wiki/Modern_portfolio_theory|mean-variance model]] with agent's linear indifference curves toward risk in order to find the optimal assets portfolio under risk. |

You have to provide PortOpt (in text files or - if you use the api- using your own code) the variance/covariance matrix of the assets, their average returns and the agent risk preference. | You have to provide PortOpt (in text files or - if you use the api- using your own code) the variance/covariance matrix of the assets, their average returns and the agent risk preference. | ||

- | It returns the vector of assets'shares that compose the optimal portfolio. | + | It returns the vector of assets' shares that compose the optimal portfolio. |

In order to minimise the variance it internally uses [[http://quadprog.sourceforge.net/|QuadProg++]], a library that implement the algorithm of Goldfarb and Idnani for the solution of a (convex) Quadratic Programming problem by means of an active-set dual method. | In order to minimise the variance it internally uses [[http://quadprog.sourceforge.net/|QuadProg++]], a library that implement the algorithm of Goldfarb and Idnani for the solution of a (convex) Quadratic Programming problem by means of an active-set dual method. | ||

Line 11: | Line 11: | ||

===== Download it ===== | ===== Download it ===== | ||

- | * windows executable (command line tool!) | + | Windows executable (command line tool!), linux (x64) executable and source code (for C++/Python) are available from [[https://sourceforge.net/projects/portopt |SourceForge]]. |

- | * {{:personal:portfolio:portopt_executable.tgz|linux (x64) executable}} | + | |

- | * {{:personal:portfolio:portopt_source.tgz|source}} (for C++/Python) | + | ===== Bugs and support ===== |

+ | | ||

+ | If you find a bug, request a feature or need support open a ticket or discuss it in the [[https://sourceforge.net/projects/portopt |SourceForge]] pages. | ||

===== Theorical Background ===== | ===== Theorical Background ===== | ||

Line 19: | Line 21: | ||

In portfolio theory agents attempts to maximise portfolio expected return for a given amount of portfolio risk, or equivalently to minimise risk for a given level of expected return. | In portfolio theory agents attempts to maximise portfolio expected return for a given amount of portfolio risk, or equivalently to minimise risk for a given level of expected return. | ||

- | {{ :personal:portfolio:portfolio_graph.png?nolink |Theoretical framework}} | + | {{ :personal:portfolio:portfolio_model.png?nolink |Theoretical framework}} |

The portfolio management can be portrayed graphically as in the above Figure, where the feasible set of variance-profitability combinations in enclosed by the blue curve and the B-D segment represents the efficient frontier, where no variance can be lowered at productivity's price or equivalently no productivity can be increased at price of increasing variance. | The portfolio management can be portrayed graphically as in the above Figure, where the feasible set of variance-profitability combinations in enclosed by the blue curve and the B-D segment represents the efficient frontier, where no variance can be lowered at productivity's price or equivalently no productivity can be increased at price of increasing variance. | ||

Line 26: | Line 28: | ||

In such case the indifference curves can be drawn like a bundle of straight lines having equation $prod = \alpha * var + \beta$, where $\alpha$ is the linear risk aversion coefficient and both $prod$ and $var$ refer to the overall portfolio's productivity and variance. | In such case the indifference curves can be drawn like a bundle of straight lines having equation $prod = \alpha * var + \beta$, where $\alpha$ is the linear risk aversion coefficient and both $prod$ and $var$ refer to the overall portfolio's productivity and variance. | ||

- | Point $B$ represents the point having the lowest possible portfolio variance. Agents with $alpha$ risk aversion will choose however the tangent point $C$ that can be obtained by solving the following quadratic problem: | + | Point $B$ represents the point having the lowest possible portfolio variance. Agents with $\alpha$ risk aversion will choose however the tangent point $C$ that can be obtained by solving the following quadratic problem: |

\begin{equation} | \begin{equation} | ||

Line 52: | Line 54: | ||

\end{equation} | \end{equation} | ||

- | where $x_i$ is the share of the asset $i$, $p_i$ is its productivity and hence $\sum_i {x_i p_i}$ is the overall portfolio productivity and $\sum_i { \sum_j { x_i x_j \sigma_{i,j}}}$ its variance. | + | where $x_i$ is the share of the asset $i$, $p_i$ is its productivity, $\sigma_{i,j}$ is the covariance between assets $i$ and $j$ and hence $\sum_i {x_i p_i}$ is the overall portfolio productivity and $\sum_i { \sum_j { x_i x_j \sigma_{i,j}}}$ is its variance. |

As the only quadratic term arises when $i=j$ and $\sigma_{i,j}$ being the variance is always positive, the problem is convex and hence easily numerically solved. | As the only quadratic term arises when $i=j$ and $\sigma_{i,j}$ being the variance is always positive, the problem is convex and hence easily numerically solved. | ||

Line 79: | Line 81: | ||

g++ -std=c++0x -O -shared -Wl,-soname,_portopt.so -o _portopt.so QuadProg++.o Array.o anyoption.o portopt.o portopt_wrap.o | g++ -std=c++0x -O -shared -Wl,-soname,_portopt.so -o _portopt.so QuadProg++.o Array.o anyoption.o portopt.o portopt_wrap.o | ||

(then please refer to the python example for usage) | (then please refer to the python example for usage) | ||

+ | |||

+ | If you want to change the output library name (e.g. you want to create _portopt_p3.so for python3 alongside _portopt.so for python2), do it in the %module variable of portopt.i and in the -soname and -o options of the linking command (and don't forget to use the right python included directory in the compilation command).\\ | ||

+ | You can then load the correct module in your script with something like: | ||

+ | import sys | ||

+ | if sys.version_info < (3, 0): | ||

+ | import portopt | ||

+ | else: | ||

+ | import portopt_p3 as portopt | ||

===== Usage ===== | ===== Usage ===== | ||

+ | |||

+ | :!: Please notice that the API changed from version 1.1, with the introduction of the ''port_opt_mean'' and ''port_opt_var'' parameters (both by reference). For the old 1.1 call instructions see [[https://lobianco.org/antonello/personal:portfolio:portopt?rev=1441891152|here]]. | ||

+ | |||

+ | |||

== Linux == | == Linux == | ||

./portopt [options] | ./portopt [options] | ||

Line 91: | Line 105: | ||

Call: | Call: | ||

- | double solveport (const vector< vector <double> > &VAR, const vector<double> &MEANS, const double &alpha, vector<double> &x_h, int &errorcode) | + | double solveport (const vector< vector <double> > &VAR, const vector<double> &MEANS, const double &alpha, vector<double> &x_h, int &errorcode, string &errormessage, double &port_opt_mean, double &port_opt_var, const double tollerance = 0.000001) |

| | ||

- | == As a lib ising Python: == | + | == As a lib using Python: == |

import portopt | import portopt | ||

- | results = portopt.solveport(var,means,alpha) | + | results = portopt.solveport(var,means,alpha,tolerance) # tolerance is optional, default to 0.000001 |

+ | functioncost = results[0] | ||

+ | shares = results[1] | ||

+ | errorcode = results[2] | ||

+ | errormessage = results[3] | ||

+ | opt_mean = results[4] | ||

+ | opt_var = results[5] | ||

=== Options === | === Options === | ||

<code> | <code> | ||

- | -h --help Prints this help | + | -h --help Prints this help |

-v --var-file [input_var_file_name] Input file containing the variance/covariance matrix (relative path) | -v --var-file [input_var_file_name] Input file containing the variance/covariance matrix (relative path) | ||

-m --means-file [input_means_file_name] Input file containing the means vector (relative path) | -m --means-file [input_means_file_name] Input file containing the means vector (relative path) | ||

-a --alpha [alpha_coefficient] Coefficient between production and risk in the linear indifference curves | -a --alpha [alpha_coefficient] Coefficient between production and risk in the linear indifference curves | ||

-f --field-delimiter [field_delimiter] Character to use as field delimiter (default: ';') | -f --field-delimiter [field_delimiter] Character to use as field delimiter (default: ';') | ||

- | -s --decimal-separator [decimal-separator] Character to use as decimal delimiter (default: '.')'' | + | -s --decimal-separator [decimal-separator] Character to use as decimal delimiter (default: '.') |

+ | -t --tollerance [tolerance] A tolerance level to distinguish from zero (default: 0.000001) | ||

</code> | </code> | ||

Line 111: | Line 132: | ||

* Higher the alpha, lower the agent risk aversion; | * Higher the alpha, lower the agent risk aversion; | ||

* Set a negative alpha to retrieve the portfolio with the lowest possible variance; | * Set a negative alpha to retrieve the portfolio with the lowest possible variance; | ||

- | * Set alpha to zero to retrieve the portfolio with the highest mean, indipendently from variance (solution not guaranteed to be unique); | + | * Set alpha to zero to retrieve the portfolio with the highest mean, independently from variance (solution not guaranteed to be unique); |

- | * Assets shares are returned in the x_h vector, eventual error code (0: all fine, 1: input data error, 2: no solutions) in the errorcode parameter. | + | * Assets shares are returned in the x_h vector, eventual error code (0: all fine, 1: input data error, 2: no solutions, 3: didn't solve, 4: solver internal error) in the errorcode parameter. |

+ | * Use option "tollerance" with two l up to version 1.1 included | ||

| | ||

| | ||

Line 124: | Line 146: | ||

You should have received a copy of the GNU Lesser General Public License along with PortOpt. If not, see [[http://www.gnu.org/licenses]]. | You should have received a copy of the GNU Lesser General Public License along with PortOpt. If not, see [[http://www.gnu.org/licenses]]. | ||

+ | |||

+ | |||

+ | ===== Citations ===== | ||

+ | If you use this program or a derivative of it in an academic framework, please cite it!\\ | ||

+ | Please cite as: | ||

+ | * A. Dragicevic, A. Lobianco, A. Leblois (2016), "[[http://dx.doi.org/10.1016/j.forpol.2015.12.010|Forest planning and productivity-risk trade-off through the Markowitz mean-variance model]]", Forest Policy and Economics, Volume 64, March 2016, Pages 25–34. | ||

+ | |||

+ | ===== Acknowledgements ===== | ||

+ | |||

+ | This work was supported by: | ||

+ | |||

+ | * a grant overseen by Office National des Forêts through the [[http://www.foretspourdemain.fr |Forêts pour Demain International Teaching and Research Chair]]; | ||

+ | * the French National Research Agency through the [[http://mycor.nancy.inra.fr/ARBRE/ |Laboratory of Excellence ARBRE]], a part of the "Investissements d'Avenir" Program (ANR 11 -- LABX-0002-01). | ||

+ | |||