Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
braverock
GitHub Repository: braverock/portfolioanalytics
Path: blob/master/sandbox/benchmarking/performance_considerations.txt
1433 views
1
Version: 0.8.3
2
12/17/2013
3
4
The functions described in the paragraphs below should be monitored and considered for any degradation in performance.
5
6
optimize.portfolio() is the main function for portfolio optimization. The default function to calculate the portfolio moments is set.portfolio.moments(). The set.portfolio.moments() function should calculate the moments once in optimize.portfolio() and then pass the moments to constrained_objective(). constrained_objective() is the objective function for DEoptim, random portfolios, pso, and GenSA. There is a check in constrained_objective() that will calculate the moments if they are not set correctly in optimize.portfolio(). This can be very expensive in terms of performance because constrained_objective() is potentially called thousands or tens of thousands of times.
7
8
random_portfolios() calculates a number of portfolios that satisfy weight_sum, box, group, and position limit constraints. There are 3 methods to calculate a random set of weights:
9
1) sample, 2) uniform, and 3) grid. The uniform and grid methods are relatively fast and the sample method has the potential to be slower.
10
11
Generating random portfolios with the sample method is a “brute force search” method to generate a random set of weights and can potentially be slow depending on the number of assets and combination of constraints. The sample method to generate a random set of weights is relatively fast for sum of weights, box, and position limit constraints. Including group constraints or making the constraints restrictive will increase runtime of the function. rp_sample() only handles weight_sum and box constraints. Group and position limit constraints are handled in rp_transform(), which is called in randomize_portfolio. rp_transform() uses logic from random portfolios so any improvement should be implemented in both functions. fn_map() is a wrapper for rp_transform and is used in the mapping function for DEoptim so any improvement here could be a performance gain for optimization with DEoptim.
12
13
For optimize_method=”DEoptim”, the initial population is calculated with random_portfolios(). A set of random portfolios can be passed in by the user with the “rp” argument. If “rp” is not passed in, then we generate random portfolios in optimize.portfolio() used for the initial population. For a single period optimization with optimize.portfolio(), the random portfolios are only generated once. However, optimize.portfolio.rebalancing() is a wrapper for optimize.portfolio() to manage the time index to pass the returns to optimize.portfolio() for out of sample portfolio optimization with rebalancing . This results in multiple calls to optimize.portfolio(). For optimize_method=”random” and optimize_method=”DEoptim”, the random portfolios should only be generated once. Generating random portfolios at each call to optimize.portfolio() is redundant and negatively impacts performance.
14