## Troubleshooting Portfolio Optimization Results

### Portfolio Object Destroyed When Modifying

If a `Portfolio`

object is destroyed when modifying, remember to
pass an existing object into the `Portfolio`

object if you want to
modify it, otherwise it creates a new object. See Creating the Portfolio Object for details.

### Optimization Fails with “Bad Pivot” Message

If the optimization fails with a "bad pivot" message from
`lcprog`

, try a larger value for `tolpiv`

which is a tolerance for pivot selection in the `lcprog`

algorithm
(try `1.0e-7`

, for example) or try the
`interior-point-convex`

version of `quadprog`

. For details, see Choosing and Controlling the Solver for Mean-Variance Portfolio Optimization, the help header for
`lcprog`

, and `quadprog`

.

### Speed of Optimization

Although it is difficult to characterize when one algorithm is faster than the
other, the default solver, `lcprog`

is faster for smaller problems
and the `quadprog`

solver is faster for larger problems. If one
solver seems to take too much time, try the other solver. To change solvers, use
`setSolver`

.

### Matrix Incompatibility and "Non-Conformable" Errors

If you get matrix incompatibility or "non-conformable" errors, the representation of data in the tools follows a specific set of basic rules described in Conventions for Representation of Data.

### Missing Data Estimation Fails

If asset return data has missing or `NaN`

values, the `estimateAssetMoments`

function with
the `'missingdata'`

flag set to `true`

may fail
with either too many iterations or a singular covariance. To correct this problem,
consider this:

If you have asset return data with no missing or

`NaN`

values, you can compute a covariance matrix that may be singular without difficulties. If you have missing or`NaN`

values in your data, the supported missing data feature requires that your covariance matrix must be positive-definite, that is, nonsingular.`estimateAssetMoments`

uses default settings for the missing data estimation procedure that might not be appropriate for all problems.

In either case, you might want to estimate the moments of asset
returns separately with either the ECM estimation functions such as `ecmnmle`

or with your own
functions.

`mv_optim_transform`

Errors

If you obtain optimization errors such as:

Error using mv_optim_transform (line 233) Portfolio set appears to be either empty or unbounded. Check constraints. Error in Portfolio/estimateFrontier (line 63) [A, b, f0, f, H, g, lb] = mv_optim_transform(obj);

Error using mv_optim_transform (line 238) Cannot obtain finite lower bounds for specified portfolio set. Error in Portfolio/estimateFrontier (line 63) [A, b, f0, f, H, g, lb] = mv_optim_transform(obj);

`estimateBounds`

to examine your
portfolio set, and use `checkFeasibility`

to ensure that
your initial portfolio is either feasible and, if infeasible, that you have
sufficient turnover to get from your initial portfolio to the portfolio set.
**Tip**

To correct this problem, try solving your problem with larger values for turnover or tracking-error and gradually reduce to the value that you want.

`solveContinuousCustomObjProb`

or `solveMICustomObjProb`

Errors

These errors can occur if the portfolio set is empty or unbounded. If the
portfolio set is empty, the error states that the problem is infeasible. The best
way to deal with these problems is to use the validation functions in Validate the Portfolio Problem for Portfolio Object.
Specifically, use `estimateBounds`

to examine your
portfolio set, and use `checkFeasibility`

to ensure that
your initial portfolio is either feasible or, if infeasible, that you have
sufficient turnover to get from your initial portfolio to the portfolio set.

### Efficient Portfolios Do Not Make Sense

If you obtain efficient portfolios that do not seem to make sense, this can happen
if you forget to set specific constraints or you set incorrect constraints. For
example, if you allow portfolio weights to fall between `0`

and
`1`

and do not set a budget constraint, you can get portfolios
that are 100% invested in every asset. Although it may be hard to detect, the best
thing to do is to review the constraints you have set with display of the object. If
you get portfolios with 100% invested in each asset, you can review the display of
your object and quickly see that no budget constraint is set. Also, you can use
`estimateBounds`

and `checkFeasibility`

to determine if
the bounds for your portfolio set make sense and to determine if the portfolios you
obtained are feasible relative to an independent formulation of your portfolio
set.

### Efficient Frontiers Do Not Make Sense

If you obtain efficient frontiers that do not seem to make sense, this can happen
for some cases of mean and covariance of asset returns. It is possible for some
mean-variance portfolio optimization problems to have difficulties at the endpoints
of the efficient frontier. It is rare for standard portfolio problems, but this can
occur. For example, this can occur when using unusual combinations of turnover
constraints and transaction costs. Usually, the workaround of setting the hidden
property `enforcePareto`

produces a single portfolio for the entire
efficient frontier, where any other solutions are not Pareto optimal (which is what
efficient portfolios must be).

An example of a portfolio optimization problem that has difficulties at the endpoints of the efficient frontier is this standard mean-variance portfolio problem (long-only with a budget constraint) with the following mean and covariance of asset returns:

m = [ 1; 2; 3 ]; C = [ 1 1 0; 1 1 0; 0 0 1 ]; p = Portfolio; p = Portfolio(p, 'assetmean', m, 'assetcovar', C); p = Portfolio(p, 'lowerbudget', 1, 'upperbudget', 1); p = Portfolio(p, 'lowerbound', 0); plotFrontier(p)

To work around this problem, set the hidden Portfolio object property for
`enforcePareto`

. This property instructs the optimizer to
perform extra steps to ensure a Pareto-optimal solution. This slows down the solver,
but guarantees a Pareto-optimal solution.

p.enforcePareto = true; plotFrontier(p)

### Troubleshooting `estimateCustomObjectivePortfolio`

When using `estimateCustomObjectivePortfolio`

, nonconvex functions are not
supported for problems with cardinality constraints or conditional bounds.
Specifically, the following error displays when using `estimateCustomObjectivePortfolio`

with a `Portfolio`

object that includes
`'Conditional'`

`BoundType`

(semicontinuous) constraints using `setBounds`

or
`MinNumAssets`

and `MaxNumAssets`

(cardinality) constraints using `setMinMaxNumAssets`

.

Error using solveMICustomObjProb Objective function must be convex in problems with cardinality constraints and/or conditional bounds. Error in Portfolio/estimateCustomObjectivePortfolio (line 88) [pwgt,exitflag] = solveMICustomObjProb(obj,prob,fun,flags);

**Note**

This error applies only to quadratic functions. This error is not detected in nonlinear functions. Therefore, if you are using a nonlinear function, you must validate your input.

For more information, see Role of Convexity in Portfolio Problems.

### Troubleshooting for Setting `'Conditional'`

`BoundType`

, `MinNumAssets`

, and
`MaxNumAssets`

Constraints

When configuring a `Portfolio`

, `PortfolioCVaR`

, or `PortfolioMAD`

object to include
`'Conditional'`

`BoundType`

(semicontinuous) constraints using `setBounds`

or
`MinNumAssets`

and `MaxNumAssets`

(cardinality) constraints using `setMinMaxNumAssets`

, the values of the inputs that you supply can result
in warning messages.

#### Conditional Bounds with `LowerBound`

Defined as Empty or Zero

When using `setBounds`

with
the `BoundType`

set to `'Conditional'`

and the
`LowerBound`

input argument is empty (```
[
]
```

) or `0`

, the `Conditional`

bound is not effective and is equivalent to a `Simple`

bound.

AssetMean = [ 0.0101110; 0.0043532; 0.0137058 ]; AssetCovar = [ 0.00324625 0.00022983 0.00420395; 0.00022983 0.00049937 0.00019247; 0.00420395 0.00019247 0.00764097 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar, 'Budget', 1); p = setBounds(p, 0, 0.5, 'BoundType', 'Conditional'); p = setMinMaxNumAssets(p, 3, 3); estimateFrontier(p, 10)

Warning: Conditional bounds with 'LowerBound' as zero are equivalent to simple bounds. Consider either using strictly positive 'LowerBound' or 'simple' as the 'BoundType' instead. > In internal.finance.PortfolioMixedInteger/checkBoundType (line 46) In Portfolio/checkarguments (line 204) In Portfolio/setBounds (line 80) Warning: The solution may have less than 'MinNumAssets' assets with nonzero weight. To enforce 'MinNumAssets' requirement, set strictly positive lower conditional bounds. > In internal.finance.PortfolioMixedInteger/hasIntegerConstraints (line 44) In Portfolio/estimateFrontier (line 51) ans = Columns 1 through 8 0.5000 0.3555 0.3011 0.3299 0.3585 0.3873 0.4160 0.4448 0.5000 0.5000 0.4653 0.3987 0.3322 0.2655 0.1989 0.1323 0.0000 0.1445 0.2335 0.2714 0.3093 0.3472 0.3850 0.4229 Columns 9 through 10 0.4735 0.5000 0.0657 0 0.4608 0.5000

In all the 10 optimal allocations, there are allocations (the first and last
ones) that only have two assets, which is in conflict with the
`MinNumAssets`

constraint that three assets should be
allocated. Also there are two warnings, which actually explain what happens. In
this case, the `'Conditional'`

bound constraints are defined as
`xi`

= `0`

or `0`

<=
`xi`

<= `0.5`

, which are internally
modeled as
`0`

**vi*<=xi<=`0.5`

**vi*,
where *vi* is `0`

or `1`

,
where `0`

indicates not allocated, and `1`

indicates allocated. Here, *vi*=`1`

, which
still allows the asset to have a weight of `0`

. In other words,
setting `LowerBound`

as `0`

or empty, doesn’t
clearly define the minimum allocation for an allocated asset. Therefore, a
`0`

weighted asset is also considered as an allocated
asset. To fix this warning, follow the instructions in the warning message, and
set a `LowerBound`

value that is strictly
positive.

AssetMean = [ 0.0101110; 0.0043532; 0.0137058 ]; AssetCovar = [ 0.00324625 0.00022983 0.00420395; 0.00022983 0.00049937 0.00019247; 0.00420395 0.00019247 0.00764097 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar, 'Budget', 1); p = setBounds(p, 0.3, 0.5, 'BoundType', 'Conditional'); p = setMinMaxNumAssets(p, 3, 3); estimateFrontier(p, 10)

ans = Columns 1 through 8 0.3000 0.3180 0.3353 0.3489 0.3580 0.3638 0.3694 0.3576 0.4000 0.3820 0.3642 0.3479 0.3333 0.3199 0.3067 0.3001 0.3000 0.3000 0.3005 0.3032 0.3088 0.3163 0.3240 0.3423 Columns 9 through 10 0.3289 0.3000 0.3000 0.3000 0.3711 0.4000

#### Length of `'BoundType'`

Must Be Conformable with `NumAssets`

The `setBounds`

optional name-value argument for `'BoundType'`

must be defined
for all assets in a `Portfolio`

, `PortfolioCVaR`

, or `PortfolioMAD`

object. By default,
the `'BoundType'`

is `'Simple'`

and applies to
all assets. Using `setBounds`

, you
can choose to define a `'BoundType'`

for each asset. In this
case, the number of `'BoundType'`

specifications must match the
number of assets (`NumAssets`

) in the `Portfolio`

, `PortfolioCVaR`

, or `PortfolioMAD`

object. The
following example demonstrates the error when the number of
`'BoundType'`

specifications do not match the number of
assets in the `Portfolio`

object.

AssetMean = [ 0.0101110; 0.0043532; 0.0137058 ]; AssetCovar = [ 0.00324625 0.00022983 0.00420395; 0.00022983 0.00049937 0.00019247; 0.00420395 0.00019247 0.00764097 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar, 'Budget', 1); p = setBounds(p, 0.1, 0.5, 'BoundType',["simple"; "conditional"])

Cannot create bound constraints. Caused by: Error using internal.finance.PortfolioMixedInteger/checkBoundType (line 28) Length of 'BoundType' must be conformable with 'NumAssets'=3.

To correct this, modify the `BoundType`

to include three
specifications because the `Portfolio`

object has three
assets.

AssetMean = [ 0.0101110; 0.0043532; 0.0137058 ]; AssetCovar = [ 0.00324625 0.00022983 0.00420395; 0.00022983 0.00049937 0.00019247; 0.00420395 0.00019247 0.00764097 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar, 'Budget', 1); p = setBounds(p, 0.1, 0.5, 'BoundType',["simple"; "conditional";"conditional"]) p.BoundType

p = Portfolio with properties: BuyCost: [] SellCost: [] RiskFreeRate: [] AssetMean: [3×1 double] AssetCovar: [3×3 double] TrackingError: [] TrackingPort: [] Turnover: [] BuyTurnover: [] SellTurnover: [] Name: [] NumAssets: 3 AssetList: [] InitPort: [] AInequality: [] bInequality: [] AEquality: [] bEquality: [] LowerBound: [3×1 double] UpperBound: [3×1 double] LowerBudget: 1 UpperBudget: 1 GroupMatrix: [] LowerGroup: [] UpperGroup: [] GroupA: [] GroupB: [] LowerRatio: [] UpperRatio: [] BoundType: [3×1 categorical] MinNumAssets: [] MaxNumAssets: [] ans = 3×1 categorical array simple conditional conditional

#### Redundant Constraints from `'BoundType'`

, `'MinNumAssets'`

, `'MaxNumAssets'`

Constraints

When none of the constraints from `'BoundType'`

,
`'MinNumAssets'`

, or `'MaxNumAssets'`

are
active, the redundant constraints from `'BoundType'`

,
`'MinNumAssets'`

, `'MaxNumAssets'`

warning
occurs. This happens when you explicitly use `setBounds`

and
`setMinMaxNumAssets`

but with values that are inactive. That is,
the `'Conditional'`

`BoundType`

has a `LowerBound`

= ```
[
]
```

or `0`

, `'MinNumAssets'`

is
`0`

, or `'MaxNumAssets'`

is the same value
as `NumAssets`

. In other words, if any of these three are
active, the warning will not show up when using the `estimate`

functions or `plotFrontier`

. The following two
examples show the rationale.

The first example is when the `BoundType`

is explicitly set
as `'Conditional'`

but the `LowerBound`

is
`0`

, and no `'MinNumAssets'`

and
`'MaxNumAssets'`

constraints are defined using `setMinMaxNumAssets`

.

AssetMean = [ 0.0101110; 0.0043532; 0.0137058 ]; AssetCovar = [ 0.00324625 0.00022983 0.00420395; 0.00022983 0.00049937 0.00019247; 0.00420395 0.00019247 0.00764097 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar, 'Budget', 1); p = setBounds(p, 0, 0.5, 'BoundType', 'Conditional'); estimateFrontier(p, 10)

Warning: Redundant constraints from 'BoundType', 'MinNumAssets', 'MaxNumAssets'. > In internal.finance.PortfolioMixedInteger/hasIntegerConstraints (line 24) In Portfolio/estimateFrontier (line 51) ans = Columns 1 through 8 0.5000 0.3555 0.3011 0.3299 0.3586 0.3873 0.4160 0.4448 0.5000 0.5000 0.4653 0.3987 0.3321 0.2655 0.1989 0.1323 0 0.1445 0.2335 0.2714 0.3093 0.3471 0.3850 0.4229 Columns 9 through 10 0.4735 0.5000 0.0657 0 0.4608 0.5000

The second example is when you explicitly set the three constraints, but all
with inactive values. In this example, the `BoundType`

is
`'Conditional'`

and the `LowerBound`

is
`0`

, thus specifying ineffective
`'Conditional'`

`BoundType`

constraints, and the
`'MinNumAssets'`

and `'MaxNumAssets'`

values are `0`

and `3`

, respectively. The
`setMinMaxNumAssets`

function specifies ineffective
`'MinNumAssets'`

and `'MaxNumAssets'`

constraints.

AssetMean = [ 0.0101110; 0.0043532; 0.0137058 ]; AssetCovar = [ 0.00324625 0.00022983 0.00420395; 0.00022983 0.00049937 0.00019247; 0.00420395 0.00019247 0.00764097 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar, 'Budget', 1); p = setBounds(p, 0, 0.5, 'BoundType', 'Conditional'); p = setMinMaxNumAssets(p, 0, 3); estimateFrontier(p, 10)

Warning: Redundant constraints from 'BoundType', 'MinNumAssets', 'MaxNumAssets'. > In internal.finance.PortfolioMixedInteger/hasIntegerConstraints (line 24) In Portfolio/estimateFrontier (line 51) ans = Columns 1 through 8 0.5000 0.3555 0.3011 0.3299 0.3586 0.3873 0.4160 0.4448 0.5000 0.5000 0.4653 0.3987 0.3321 0.2655 0.1989 0.1323 0 0.1445 0.2335 0.2714 0.3093 0.3471 0.3850 0.4229 Columns 9 through 10 0.4735 0.5000 0.0657 0 0.4608 0.5000

#### Infeasible Portfolio Problem with `'BoundType'`

, `'MinNumAssets'`

, `'MaxNumAssets'`

The `Portfolio`

, `PortfolioCVaR`

, or `PortfolioMAD`

object performs
validations of all the constraints that you set before solving any specific
optimization problems. The `Portfolio`

, `PortfolioCVaR`

, or `PortfolioMAD`

object first
considers all constraints other than `'Conditional'`

`BoundType`

, `'MinNumAssets'`

, and
`'MaxNumAssets'`

and issues an error message if they are
not compatible. Then the `Portfolio`

, `PortfolioCVaR`

, or `PortfolioMAD`

object adds the
three constraints to check if they are compatible with the already checked
constraints. This separation is natural because `'Conditional'`

`BoundType`

, `'MinNumAssets'`

, and
`'MaxNumAssets'`

require additional binary variables in the
mathematical formulation that leads to a MINLP, while other constraints only
need continuous variables. You can follow the error messages to check when the
infeasible problem occurs and take actions to fix the constraints.

One possible scenario is when the `BoundType`

is
`'Conditional'`

and Groups are defined for the
`Portfolio`

object. In this case, the Group definitions are
themselves in conflict. Consequently, the `'Conditional'`

bound
constraint cannot be applied when running `estimateFrontierLimits`

.

AssetMean = [ 0.0101110; 0.0043532; 0.0137058 ]; AssetCovar = [ 0.00324625 0.00022983 0.00420395; 0.00022983 0.00049937 0.00019247; 0.00420395 0.00019247 0.00764097 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar, 'Budget', 1); p = setBounds(p, 0.1, 0.5, 'BoundType','Conditional'); p = setGroups(p, [1,1,0], 0.3, 0.5); p = addGroups(p, [0,1,0], 0.6, 0.7); pwgt = estimateFrontierLimits(p)

Error using Portfolio/buildMixedIntegerProblem (line 31) Infeasible portfolio problem prior to considering 'BoundType', 'MinNumAssets', 'MaxNumAssets'. Verify if constraints from groups, bounds, group ratios, inequality, equality, etc. are compatible. Error in Portfolio/estimateFrontierLimits>int_frontierLimits (line 93) ProbStruct = buildMixedIntegerProblem(obj); Error in Portfolio/estimateFrontierLimits (line 73) pwgt = int_frontierLimits(obj, minsolution, maxsolution);

To correct this error, change the `LowerGroup`

in the
`addGroups`

function to also be
`0.3`

to match the `GroupMatrix`

input
from `setGroups`

.

AssetMean = [ 0.0101110; 0.0043532; 0.0137058 ]; AssetCovar = [ 0.00324625 0.00022983 0.00420395; 0.00022983 0.00049937 0.00019247; 0.00420395 0.00019247 0.00764097 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar, 'Budget', 1); p = setBounds(p, 0.1, 0.5, 'BoundType','Conditional'); p = setGroups(p, [1,1,0], 0.3, 0.5); p = addGroups(p, [0,1,0], 0.3, 0.7); pwgt = estimateFrontierLimits(p)

pwgt = 0 0.2000 0.5000 0.3000 0.5000 0.5000

A second possible scenario is when the `BoundType`

is
`'Conditional'`

and the `setEquality`

function is used
with the `bEquality`

parameter set to `0.04`

.
This sets an equality constraint to have *x*1 +
*x*3 = `0.04`

. At the same time, `setBounds`

also
set the semicontinuous constraints to have *xi* =
`0`

or `0.1`

<= *xi*
<= `2.5`

, which lead to *x*1 +
`x`

3 = `0`

or `0.1`

<=
*x*1 + *x*3 <= `5`

.
The semicontinuous constraints are not compatible with the equality constraint
because there is no way to get `x`

1 + `x`

3 to
equal `0.04`

. Therefore, the error message is
displayed.

AssetMean = [ 0.05; 0.1; 0.12; 0.18 ]; AssetCovar = [ 0.0064 0.00408 0.00192 0; 0.00408 0.0289 0.0204 0.0119; 0.00192 0.0204 0.0576 0.0336; 0 0.0119 0.0336 0.1225 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar, 'Budget', 1); A = [ 1 0 1 0 ]; b = 0.04; p = setEquality(p, A, b); p = setBounds(p, 0.1, 2.5, 'BoundType','Conditional'); p = setMinMaxNumAssets(p, 2, 2); pwgt = estimateFrontierLimits(p)

Error using Portfolio/buildMixedIntegerProblem (line 109) Infeasible portfolio problem when considering 'BoundType', 'MinNumAssets', 'MaxNumAssets'. Verify if these are compatible with constraints from groups, bounds, group ratios, inequality, equality, etc. Error in Portfolio/estimateFrontierLimits>int_frontierLimits (line 93) ProbStruct = buildMixedIntegerProblem(obj); Error in Portfolio/estimateFrontierLimits (line 73) pwgt = int_frontierLimits(obj, minsolution, maxsolution);

To correct this error, change the `bEquality`

parameter from
`0.04`

to `.4`

.

AssetMean = [ 0.05; 0.1; 0.12; 0.18 ]; AssetCovar = [ 0.0064 0.00408 0.00192 0; 0.00408 0.0289 0.0204 0.0119; 0.00192 0.0204 0.0576 0.0336; 0 0.0119 0.0336 0.1225 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar, 'Budget', 1); A = [ 1 0 1 0 ]; b = 0.4; p = setEquality(p, A, b); p = setBounds(p, 0.1, 2.5, 'BoundType','Conditional'); p = setMinMaxNumAssets(p, 2, 2); pwgt = estimateFrontierLimits(p)

pwgt = 0.4000 0 0.6000 0 0 0.4000 0 0.6000

#### Unbounded Portfolio Problem

This error occurs when you are using a `Portfolio`

, `PortfolioCVaR`

, or `PortfolioMAD`

object and there is
no `UpperBound`

defined in `setBounds`

and
you are using `setMinMaxNumAssets`

. In this case, this is formulated as a mixed
integer programming problem and an ` UpperBound`

is required to
enforce `MinNumAssets`

and `MaxNumAssets`

constraints.

The optimizer first attempts to estimate the upper bound of each asset, based
on all the specified constraints. If the `UpperBound`

cannot be
found, an error message occurs which instructs you to set an explicit
`UpperBound`

. In most cases, as long as you set some upper
bounds to the problem using any `set`

function, the optimizer
can successfully find a good
estimation.

AssetMean = [ 0.05; 0.1; 0.12; 0.18 ]; AssetCovar = [ 0.0064 0.00408 0.00192 0; 0.00408 0.0289 0.0204 0.0119; 0.00192 0.0204 0.0576 0.0336; 0 0.0119 0.0336 0.1225 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar); p = setBounds(p, 0.1, 'BoundType','Conditional'); p = setGroups(p, [1,1,1,0], 0.3, 0.5); p = setMinMaxNumAssets(p, 3, 3); pwgt = estimateFrontierLimits(p)

Error using Portfolio/buildMixedIntegerProblem (line 42) Unbounded portfolio problem. Upper bounds cannot be inferred from the existing constraints. Set finite upper bounds using 'setBounds'. Error in Portfolio/estimateFrontierLimits>int_frontierLimits (line 93) ProbStruct = buildMixedIntegerProblem(obj); Error in Portfolio/estimateFrontierLimits (line 73) pwgt = int_frontierLimits(obj, minsolution, maxsolution);

To correct this error, specify an `UpperBound`

value for
`setBounds`

.

AssetMean = [ 0.05; 0.1; 0.12; 0.18 ]; AssetCovar = [ 0.0064 0.00408 0.00192 0; 0.00408 0.0289 0.0204 0.0119; 0.00192 0.0204 0.0576 0.0336; 0 0.0119 0.0336 0.1225 ]; p = Portfolio('AssetMean', AssetMean, 'AssetCovar', AssetCovar); p = setBounds(p, 0.1, .9, 'BoundType','Conditional'); p = setGroups(p, [1,1,1,0], 0.3, 0.5); p = setMinMaxNumAssets(p, 3, 3); pwgt = estimateFrontierLimits(p)

pwgt = 0.1000 0 0.1000 0.1000 0.1000 0.4000 0 0.9000

#### Total Number of Portfolio Weights with a Value > 0 Are Greater Than `MaxNumAssets`

Specified

When using a `Portfolio`

, `PortfolioCVaR`

, or `PortfolioMAD`

object, the optimal
allocation `w`

may contain some very small values that leads to
`sum`

(`w`

>`0`

) larger
than `MaxNumAssets`

, even though the
`MaxNumAssets`

constraint is specified using `setMinMaxNumAssets`

. For example, in the following code when
`setMinMaxNumAssets`

is used to set
`MaxNumAssets`

to `15`

, the
`sum`

(`w`

>`0`

) indicates
that there are `19`

assets. A close examination of the weights
shows that the weights are extremely small and are actually
0.

T = readtable('dowPortfolio.xlsx'); symbol = T.Properties.VariableNames(3:end); assetReturn = tick2ret(T{:,3:end}); p = Portfolio('AssetList', symbol, 'budget', 1); p = setMinMaxNumAssets(p, 10, 15); p = estimateAssetMoments(p,assetReturn); p = setBounds(p,0.01,0.5,'BoundType','Conditional','NumAssets',30); p = setTrackingError(p,0.05,ones(1, p.NumAssets)/p.NumAssets); w = estimateFrontierLimits(p,'min'); % minimum risk portfolio sum(w>0) % Number of assets that are allocated in the optimal portfolio w(w<eps) % Check the weights of the very small weighted assets

ans = 19 ans = 1.0e-20 * -0.0000 0 0 0.0293 0 0.3626 0.2494 0 0.0926 -0.0000 0 0.0020 0 0 0 0

This situation only happens when the `OuterApproximation`

algorithm is used with `setSolverMINLP`

to
solve a MINLP portfolio optimization problem. The
`OuterApproximation`

internally fixes the latest solved
integer variables and runs an NLP with `quadprog`

or `fmincon`

, which introduces numerical
issues and leads to weights that are very close to 0.

If you do not want to deal with very small values, you can use `setSolverMINLP`

to
select a different algorithm. In this example, the
`'TrustRegionCP'`

algorithm is
specified.

T = readtable('dowPortfolio.xlsx'); symbol = T.Properties.VariableNames(3:end); assetReturn = tick2ret(T{:,3:end}); p = Portfolio('AssetList', symbol, 'budget', 1); p = setMinMaxNumAssets(p, 10, 15); p = estimateAssetMoments(p,assetReturn); p = setBounds(p,0.01,0.5,'BoundType','Conditional','NumAssets',30); p = setTrackingError(p,0.05,ones(1, p.NumAssets)/p.NumAssets); p = setSolverMINLP(p,'TrustRegionCP'); w = estimateFrontierLimits(p,'min'); % minimum risk portfolio sum(w>0) % Number of assets that are allocated in the optimal portfolio w(w<eps) % The weights of the very small weighted assets are strictly zeros

ans = 14 ans = 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0

## See Also

`Portfolio`

| `estimateAssetMoments`

| `checkFeasibility`

| `setBounds`

| `setMinMaxNumAssets`

## Related Examples

- Postprocessing Results to Set Up Tradable Portfolios
- Creating the Portfolio Object
- Working with Portfolio Constraints Using Defaults
- Estimate Efficient Portfolios for Entire Efficient Frontier for Portfolio Object
- Estimate Efficient Frontiers for Portfolio Object
- Asset Allocation Case Study
- Portfolio Optimization Examples Using Financial Toolbox
- Portfolio Optimization with Semicontinuous and Cardinality Constraints
- Black-Litterman Portfolio Optimization Using Financial Toolbox
- Portfolio Optimization Using Factor Models
- Portfolio Optimization Using Social Performance Measure
- Diversify Portfolios Using Custom Objective
- Troubleshooting CVaR Portfolio Optimization Results
- Troubleshooting MAD Portfolio Optimization Results