Convex Optimization for Equal-Weight Long-Short Portfolios
Summary
The document asks how to make the absolute position weights in a six-stock long-short portfolio as equal as possible while respecting gross exposure, long exposure, and beta-adjusted net exposure limits. It proposes minimizing the variance of absolute weights, but the stated CVXPY expression fails disciplined convex programming (DCP) checks. The response recommends checking whether individual expressions, constraints, and the full optimization problem satisfy DCP rules, which can help locate the source of the violation.
The post gives portfolio beta values and sign and exposure constraints as context, but it does not provide a corrected objective or a complete solution. The proposed expression also differs between the initial question and the code example, so the exact cause of the error is not established. Readers should treat the response as a debugging pointer rather than a validated method for constructing equal-weight portfolios.
Key ideas
- The goal is to make absolute position weights similar in a constrained long-short portfolio.
- The proposed CVXPY objective triggers a DCP error, but the response does not identify the exact offending expression.
- Testing DCP compliance on expressions, constraints, and the full problem can help isolate modeling errors.
- The discussion supplies no corrected optimization objective or empirical validation.
Tags
Full text
# Objective function: as close to equal weight as possible # Objective function: as close to equal weight as possible I am having trouble coming up with a function to optimize the weights to be as equal as possible. It is a long-short portfolio with 6 positions weights is a cvx variable: [long, long, short, short, long/short, long/short] There are some constraints such as gross exposure cannot exceed 2, gross long cannot exceed 1.5. To get portfolio weights as close to equal weight as possible, one way is to minimize the variance of the absolute value of weights. ``` cvxpy.Minimize(cvx.sum_squares(cvx.sum(cvx.abs(weights)) - cvx.abs(weights)/6)) ``` But this throws "does not follow DCP rules". What's the problem in this line that causes the violation of DCP rules? More importantly, any thoughts on how to write an objective function to push weights to as equal weight as possible? Thanks! ### Clarification on my question: Here's the problem I need to solve: I have a portfolio with 6 stocks, with the following beta: [0.7, 1.5, 0.4, 0.8, 0.5, 1] Constraints: - the first two must be long, the second two must be short, the 5th and 6th stock can be long and short. - gross exposure cannot exceed 2 - leveraged long exposure cannot exceed 1.5 - beta adjusted net long or short exposure cannot exceed 0.5 ### Code ``` betas = [0.7, 1.5, 0.4, 0.8, 0.5, 1] weight_longs = cvx.Variable(2) weight_shorts = cvx.Variable(2) weight_longorshort = cvx.Variable(2) weights = cvx.hstack([weight_longs, weight_shorts, weight_longorshort]) # Constraints: bounds = [w_longs>=0.0, w_shorts<=-0.0] gross_exp = [cvx.sum(cvx.abs(weights)) <=2] lev_long = [cvx.sum(w_longs) + cvx.sum(cvx.pos(w_longorshort)) <= 1.5] beta_net_exp = [cvx.abs(cvx.sum(np.array(betas) * weights)) <= 0.5] constraints = bounds + gross_exp + lev_long + beta_net_exp # Minimize the variance of absolute value of weights to achieve close to equal weight obj_func = cvx.sum_squares(cvx.abs(weights) - cvs.abs(weights/6)) cvx.Problem(obj_func, constraints) ``` ## Answer by MonteCarloSims (score 2) https://quant.stackexchange.com/a/44636 Without knowing the exact data behind your code, it is hard to say exactly where the error may be. However, DCP errors seem to be thrown when the underlying equation is not convex - and therefore unable to minimize. Here is a great resource for troubleshooting. It walks through an example of discovering whether a specific problem is convex and/or where it breaks DCP rules. There is also a function which allows for the testing of each component of the problem: > You can test whether a problem, objective, constraint, or expression satisfies the DCP rules by calling object.is_dcp(). If the function returns False, there is a DCP error in that object.
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.