pyPortfolioAnalysis package

Submodules

pyPortfolioAnalysis.pyPortfolioAnalysis module

pyPortfolioAnalysis: Methods to optimize portfolio

Documentation is available as docstring or as HTML on https://github.com/anuragagrawaal/pyPortfolioAnalysis

Fucntions and Classes

Optimization Methods

‘HHI’ ‘VaR’ ‘VaR_portfolio’ ‘add_constraint’ ‘add_objective’ ‘black_litterman’ ‘box_constraint’ ‘cVaR_portfolio’ ‘constrained_objective’ ‘diversification’ ‘diversification_constraint’ ‘equal_weight’ ‘extract_groups’ ‘extract_objective_measure’ ‘extract_weights’ ‘factor_exposure_constraint’ ‘fn_map’ ‘generate_sequence’ ‘get_constraints’ ‘group_constraint’ ‘group_fail’ ‘inverse_volatility_weights’ ‘leverage_exposure_constraint’ ‘leverage_fail’ ‘max_sum_fail’ ‘min_sum_fail’ ‘minmax_objective’ ‘normalize_weights’ ‘optimize_portfolio’ ‘performance_metrics_objective ‘port_mean’ ‘portfolio_risk_objective’ ‘portfolio_spec’ ‘pos_limit_fail’ ‘position_limit_constraint’ ‘return_constraint’ ‘return_objective’ ‘risk_budget_objective’ ‘rp_decrease’ ‘rp_decrease_leverage’ ‘rp_increase’ ‘rp_position_limit’ ‘rp_transform’ ‘transaction_cost_constraint’ ‘turnover’ ‘turnover_constraint’ ‘turnover_objective’ ‘var_portfolio’ ‘weight_concentration_objective’ ‘weight_sum_constraint’

Plots

‘chart_efficient_frontier’ ‘chart_group_weights’ ‘chart_weights’

References

Brian G. Peterson and Peter Carl (2018). PortfolioAnalytics: Portfolio Analysis, Including Numerical Methods for Optimization of Portfolios. R package version 1.1.0. https://CRAN.R-project.org/package=PortfolioAnalytics

Boudt, Kris and Lu, Wanbo and Peeters, Benedict, Higher Order Comoments of Multifactor Models and Asset Allocation (June 16, 2014). Available at SSRN: http://ssrn.com/abstract=2409603 or http://dx.doi.org/10.2139/ssrn.2409603

Chriss, Neil A and Almgren, Robert, Portfolios from Sorts (April 27, 2005). Available at SSRN: http://ssrn.com/abstract=720041 or http://dx.doi.org/10.2139/ssrn.720041

Meucci, Attilio, The Black-Litterman Approach: Original Model and Extensions (August 1, 2008). Shorter version in, THE ENCYCLOPEDIA OF QUANTITATIVE FINANCE, Wiley, 2010. Avail- able at SSRN: http://ssrn.com/abstract=1117574 or http://dx.doi.org/10.2139/ssrn.1117574

Meucci, Attilio, Fully Flexible Views: Theory and Practice (August 8, 2008). Fully Flexible Views: Theory and Practice, Risk, Vol. 21, No. 10, pp. 97-102, October 2008. Available at SSRN: http://ssrn.com/abstract=1213325

Scherer, Bernd and Martin, Doug, Modern Portfolio Optimization. Springer. 2005.

Shaw, William Thornton, Portfolio Optimization for VAR, CVaR, Omega and Utility with General Return Distributions: A Monte Carlo Approach for Long-Only and Bounded Short Portfolios with Optional Robustness and a Simplified Approach to Covariance Matching (June 1, 2011). Available at SSRN: http://ssrn.com/abstract=1856476 or http://dx.doi.org/10.2139/ssrn.1856476

pyPortfolioAnalysis.pyPortfolioAnalysis.HHI(weights, groups=None)

The Herfindahl Hirschman Index measures the concentration of weights using this function.

Concentration of weights

weightsarray-like,

collection of weights of the portfolio.

groupsdict,

dictionary of groups.

returns the weight concentration given the weights

port_mean var_portfolio VaR cVaR

>>> # calculate HHI
>>> w = [0.2,0.3,-0.1,0.6,0.8]
>>> HHI(w)
pyPortfolioAnalysis.pyPortfolioAnalysis.VaR(R, p=0.05)

Calculate the value at risk (VaR)

This function calculates the value at risk (VaR) assuming gaussian distribution

Rpd.DataFrame object,

returns dataframe

pfloat, optional

quantile estimate

Calculates the VaR given returns

cVaR VaR_portfolio

>>> VaR(R,p = 0.01)
pyPortfolioAnalysis.pyPortfolioAnalysis.VaR_portfolio(w, R, p=0.05, mean=True)

calculate the value at risk (VaR) of a portfolio

This function calculates the value at risk (VaR) assuming gaussian distribution

warray-like,

list of weights of portfolio

Rpd.DataFrame object,

returns dataframe

pfloat, optional

quantile estimate

meanbool, default = True

mean VaR of portfolio

Calculates the VaR given portfolio weights

cVaR VaR_portfolio VaR

>>> w = [0.2,0.3,0.5]
>>> VaR_portfolio(w,R,p = 0.01)
pyPortfolioAnalysis.pyPortfolioAnalysis.add_constraint(portfolio, kind, enabled=True, **kwargs)

Add a constraint in portfolio_spec object

Main function to add or update constraint in portfolio_spec object

portfolioportfolio_spec,

an object of class portfolio_spec. see portfolio_spec

kindstr,

currently supported constraint: ’weight_sum’ (also ’leverage’ or ’weight’), ’box’, ’group’,

’turnover’,’diversification’, ’position_limit’, ’return’, ’factor_exposure’,

or ’leverage_exposure’.

enabledbool, default = True

bool to enable or disable constraints.

kwargsadditional key word arguments, optional

any additional constraint argument to be passed.

Adds constraints to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

•weight_sum, weight, leverage Specify constraint on the sum of the weights, see weight_sum_constraint •full_investment Special case to set min_sum=1 and max_sum=1 of weight sum constraints •dollar_neutral, active Special case to set min_sum=0 and max_sum=0 of weight_sum constraints •box box constraint for the individual asset weights, see box_constraint •long_only Special case to set min=0 and max=1 of box constraint •group specify the sum of weights within groups and the number of assets with non-zero weights in groups,

see group_constraint

•turnover Specify a constraint for target turnover. Turnover is calculated from a set of initial weights,

see turnover_constraint

•diversification target diversification of asset of weights, see diversification_constraint •position_limit Specify the number of non-zero,long, and/orshortpositions, see position_limit_constraint •return Specify the target mean return, see return_constraint •factor_exposure Specify risk factor exposures, see factor_exposure_constraint •leverage_exposure Specify a maximum leverage exposure, see leverage_exposure_constraint

>>> portfolio = portfolio_spec(assets = 4)
>>> # adding weight_sum cinstraint
>>> add_constraint(portfolio, kind = 'weight_sum', min_sum = 0.9, max_sum = .95)
>>> # long_only is a special kind of box constraint where minimum and maximum is positive
>>> # minimum and maximum can be list or scalars
>>> add_constraint(portfolio, kind = 'box', minimum = [0.9, -0.5,-0.5, 0.1], maximum = 1)
>>> add_constraint(portfolio, kind = 'long_only')
>>> # group constraint is used to specify min and max weights of certain asset_groups
>>> # groups must be a dict and group_min and group_max can be scalar or list
>>> add_constraint(portfolio, kind = 'group', group_min = [0.9, -0.5,-0.5, 0.1], group_max = 1,
              groups = {'eqity':[0,3], 'debt':[1,2]})
>>> # adding weight_sum constraint
>>> add_constraint(portfolio, kind = 'weight_sum', min_sum = 0.9, max_sum = .95)
>>> # special case of weight_sum is dollar_neutral/active or full_investment
>>> add_constraint(portfolio, kind = 'dollar_neutral')
>>> add_constraint(portfolio, kind = 'full_investment')
>>> #turnover constraint
>>> add_constraint(portfolio, kind = 'turnover', turnover_target = 0.1)
>>> #diversification constraint for diversification target in a portfolio
>>> add_constraint(portfolio, kind = 'diversification', div_target = 0.1)
>>> #position_limit is a constraint to restrict max position and also max long/short positions
>>> add_constraint(portfolio, kind = 'position_limit', max_pos = 3, max_pos_long = 2, max_pos_short = 2)
>>> #return constraint to add a target mean historical return to the portfolio
>>> add_constraint(portfolio, kind = 'return', return_target = 0.0018)
>>> #adds a tranaction cost constraint on portfolio
>>> add_constraint(portfolio, kind = 'transaction_cost', ptc = 0.1)
>>> #constraint on the leverage of portfolio
>>> add_constraint(portfolio, kind = 'leverage_exposure', leverage = 0.8)
>>> #Factor_exposure constraint is used to test portfolio with their impact on certaint factors
>>> # factors can be single or multiple with lower and upper limit. 
>>> # B can be a N*K matrix for N assets and K factors.
>>> # lower and upper arguments can be float for single factor and list for multiple factors
>>> add_constraint(portfolio, kind = 'factor_exposure', 
              B = np.matrix([[1.2,1.3],
                             [2.3,1.4],
                             [1.4,0.9],
                             [3.4,1.2]]),
               lower = [0.8,1.4], upper = [2,2.4])
pyPortfolioAnalysis.pyPortfolioAnalysis.add_objective(portfolio, kind, name, arguments=None, constraints=None, enabled=True, message=True, **kwargs)

This function is the primary function of adding and updating business goals in a portfolio.spec type object. General interface, including risk, return, and risk budget, to add optimization goals.

portfolioportfolio_spec,

an object of class portfolio_spec.

kindstr,

the character form of the goal to be added or changed, currently ‘return’,’ risk’, ‘risk_budget’,’ quadratic_utility’, or ‘weight_concentration’.

namestr,

The target name should correspond to a feature, although we will attempt to make allowances arguments : Default arguments to be transferred when executed on an objective function.

enabledbool, default = True

bool to enable or disable constraints.

messagebool, default = True

bool to enable or disable messages.

kwargsadditional key word arguments, optional

any additional constraint argument to be passed.

Adds objective to object portfolio_spec of the specified input.

add_objectives portfolio_risk_objectives risk_budget_objective turnover_objective minmax_objective weight_constraint_objective

In general, you will define your objective as one of the following types: ’return’, ’risk’, ’risk_budget’, or ’weight_concentration’.

These have special handling and intelligent defaults for dealing with the function most likely to be used as objectives, including mean, median, VaR, ES, etc. Objectives of type ’turnover’ and ’minmax’ are also supported.

>>> port = portfolio_spec(assets = 5)
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> add_constraint('long_only')
>>> add_constraint('full_investment')
>>> #adding objectives
>>> add_objective(kind = 'return', name = 'mean', target = 0.0018)
>>> add_objective(kind = 'portfolio_risk', name = 'std', target = 0.015)
>>> add_objective(kind = 'risk_budget', name = 'risk_budget')
>>> add_objective(kind = 'weight_conc', name = 'HHI', target = 0.11)
>>> add_objective(kind = 'performance_metrics', name = 'sharpe', target = 0.13)
>>> # add a custom objective by first defining it.
>>> def sortino_ratio(w,R):
        #SOME CODE
>>> add_objective(kind = 'performance_metrics', name = {'sortino':sortino_ratio}, target = 0.35)
NOTE: The output of sortino_ratio or other custom function in objective must be a float.
NOTE: you can also add other custom function in other kind of objective in similar methd.
class pyPortfolioAnalysis.pyPortfolioAnalysis.black_litterman(R, P)

Bases: object

A class to call black_litterman object.

Black-litterman formula is popular to get posterior moments of the portfolio.

Rpandas.DataFrame

dataframe of returns series.

Pmatrix-like,

KXN link matrix where N is the number of assets and K are the views

fit(Mu = None, S = None, Views = None, tau = 1):

returns a matrix of posterior returns based on Views and returns data.

fit(Mu=None, S=None, Views=None, tau=1)

fit method of black_litterman object

Main function to call in order to return the posterior mean of the portfolio given the views and return.

Muarray-like, optional

prior mean of the returns. numpy.mean is called if Mu is None

Smatrix-like, optional

NXN covariance matrix. numpy.cov is called if S is None

Views: array-like, default = None

array of K views held by investor.

Tau: float, default = 1

multiplying factor to be used.

array:

returns an array of posterior moments of portfolio given the returns and weights

portfolio_spec optimize_portfolio

Black-litterman formula is very useful if an investor believes that a particular stock is going to rise compared to others although this information is not incorporated in the stock price. Essentially, it captures the views an investor holds for a particular asset.

>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
                   'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> P = np.matrix([[-1, 0, 1],[0,-1,1]])
>>> Views = np.matrix([[0.02],
               [0.05]])
>>> bl = black_litterman(R = port_ret, P = P)
>>> bl.fit(Views = Views)
pyPortfolioAnalysis.pyPortfolioAnalysis.box_constraint(assets, minimum, maximum, kind='box', enabled=True, message=True, **kwargs)

The box constraint defines the upper and lower limits of asset weights. add_constraint calls this function when type=”box” is defined.

assetsint, or array-like,

number of assets, or optionally a named list of assets specifying initial weights.

minimumfloat, or array-like,

numeric or named list defining the minimum constraints of the weight box.

maximumfloat, or array-like,

numeric or named list defining the maximum constraints of the weight box.

kindstr,

string of kind of constraint.

enabledbool, default = True

bool to enable or disable constraints.

messagebool, default = True

bool to enable or disable messages.

kwargsadditional key word arguments, optional

any additional constraint argument to be passed.

Add box constraints to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

>>> add_constraint(portfolio, kind = 'box', minimum = [0.9, -0.5,-0.5, 0.1], maximum = 1)
pyPortfolioAnalysis.pyPortfolioAnalysis.cVaR_portfolio(w, R, p=0.05, mean=True)

Calculate the conditional value at risk (cVaR) of a portfolio

This function calculates the conditional value at risk (cVaR) assuming gaussian distribution

warray-like,

list of weights of portfolio

Rpd.DataFrame object,

returns dataframe

pfloat, optional

quantile estimate

meanbool, default = True

mean VaR of portfolio

Calculates the VaR given portfolio weights

cVaR VaR_portfolio VaR

>>> w = [0.2,0.3,0.5]
>>> cVaR_portfolio(w,R,p = 0.01)
pyPortfolioAnalysis.pyPortfolioAnalysis.chart_efficient_frontier(portfolio, R, metric='Sharpe Ratio', arguments={'rf': 0.0}, cml=False, rand_pf=300, optimize_method='DEoptim', alpha=0.4, figsize=(10, 6), **kwargs)

Function to plot efficient frontier of portfolio.

portfolioportfolio_spec,

an object of class portfolio_spec.

Rpandas dataframe,

dataframe of the returns series

metric: str, default = ‘Sharpe Ratio’

metric should be either of ‘Sharpe Ratio’ or ‘Treynor Ratio’

argumentsdict, optional

additional arguments such as risk-free rate in the form of a dictionary.

cmlbool, default = False

bool to enable or disable capital market line

rand_pfint, optional

random portfolio to plot to show the efficient frontier

optimize_methodstr, optional

optimize_method should be similar to those in optimize_portfolio. see optimize_portfolio

alphafloat, optional

transparency

figsizetuple, optional

figure size in the form of a tuple

kwargsadditional key word arguments, optional

any additional constraint argument to be passed.

matplotlib.scatter

chart_group_weights chart_weights chart_efficient_frontier

>>> # Rb is S&P500 benchmark for capital market line and beta for treynor ratio
>>> chart_efficient_froniter(portfolio, R, metric = 'Treynor Ratio', 
    arguments = {'rf': 0.0008, 'Rb':Rb}, cml = True, alpha = 0.1, rand_pf = 1000, optimize_method = 'pso')
pyPortfolioAnalysis.pyPortfolioAnalysis.chart_group_weights(portfolio)

Function to plot individual group weights of optimal weights.

portfolioportfolio_spec,

an object of class portfolio_spec.

matplotlib.lines.Line2D

chart_group_weights chart_efficient_frontier

>>> chart_group_weights(portfolio)
NOTE: chart_group_weights will only work after call optimize_portfolio on portfolio_spec
pyPortfolioAnalysis.pyPortfolioAnalysis.chart_weights(portfolio)

Function to plot weights of optimal weights.

portfolioportfolio_spec,

an object of class portfolio_spec.

matplotlib.lines.Line2D

chart_group_weights chart_efficient_frontier

>>> chart_weights(portfolio)
NOTE: chart_group_weights will only work after call optimize_portfolio on portfolio_spec
pyPortfolioAnalysis.pyPortfolioAnalysis.constrained_objective(w, R, portfolio, trace=False, normalize=False, storage=False, verbose=False, penalty=10000, *kwargs, **args)

Add a constraint in portfolio_spec object

Main function to add or update constraint in portfolio_spec object

warray-like,

weights to test

Rpd.DataFrame,

dataframe of returns of assets in portfolio

tracebool, default = False

bool to enable or disable constraints.

normalizebool, default = False

bool to specify if weights should be normalized first. see normalize_weights.

verbosebool, default = False

bool to enable or disable verbose argument.

penaltyint, optional

int value specifying he penalty if constraint or objective is breached.

kwargsadditional key word arguments, optional

any additional constraint argument to be passed.

kwargsadditional arguments, optional

any additional argument to be passed.

returns a float of total penalty given a weight. if trace = True, additional objective measure will be returned in the form of dictionary.

rp_transform optimize_portfolio

constrained_objective is the main function that is called by optimize_weights to optimze the constraint and objectives provided by the portfolio.

Loosely speaking, constrained_objective is very similar to an information criteria.

pyPortfolioAnalysis.pyPortfolioAnalysis.diversification(weights)

Diversification is stated as 1 minus the total of the squared weights

Diversification function to compute as a constraint

weightsarray-like,

list of weights of assets.

returns diversification given the weights

turnover

>>> w = [0.2,0.3,0.5]
>>> turnover(w)
pyPortfolioAnalysis.pyPortfolioAnalysis.diversification_constraint(assets, div_target, kind='diversification', enabled=True, message=True)

Target diversification value is specified under the diversification constraint.

This function is called by add.constraint when type=”diversification” is mentioned.

assetsInt, or array-like,

Number of assets or, as an alternative, a named asset list specifying initial weights.

div_targetfloat,

diversification target value

kindstr,

string of the kind of constraint.

enabledbool, default = True

bool to enable or disable constraints.

messagebool, default = True

bool to enable or disable messages.

Adds diversification constraints to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

>>> #diversification constraint for diversification target in a portfolio
>>> add_constraint(portfolio, kind = 'diversification', div_target = 0.1)
pyPortfolioAnalysis.pyPortfolioAnalysis.equal_weight(R, portfoio, **kwargs)

Function to extract objective measures of equal weight portfolio.

Rpd.DataFrame,

dataframe of returns of assets in portfolio

portfolioportfolio_spec,

an object of class portfolio_spec.

kwargsadditional arguments, optional

any additional argument to be passed.

dictionary of objective measures of equal weighted portfolio

inverse_volatility_weights

>>> equal_weight(R, portfolio)
pyPortfolioAnalysis.pyPortfolioAnalysis.extract_groups(portfolio)

Function to extract groups from portfolio_spec object.

portfolioportfolio_spec,

an object of class portfolio_spec.

dictionary of groups if group_constraint is specified.

extract_weights extract_objective_measure extract_groups

>>> extract_groups(portfolio)
NOTE: extract_groups will only work after calling optimize_portfolio on portfolio_spec
pyPortfolioAnalysis.pyPortfolioAnalysis.extract_objective_measure(R, portfolio, **kwargs)

Function to extract objective measures of optimal weights.

Rpd.DataFrame,

dataframe of returns of assets in portfolio

portfolioportfolio_spec,

an object of class portfolio_spec.

kwargsadditional arguments, optional

any additional argument to be passed.

dictionary of objective measures as specified in the portfolio_spec object

extract_weights extract_objective_measure extract_groups

>>> extract_objective_measure(R, portfolio)
NOTE: extract_objective_measure will only work after calling optimize_portfolio on portfolio_spec
pyPortfolioAnalysis.pyPortfolioAnalysis.extract_weights(portfolio)

Function to extract optimal weights.

portfolioportfolio_spec,

an object of class portfolio_spec.

array of optimal weights

extract_objective_measure extract_groups

>>> extract_weights(portfolio)
NOTE: extract_weights will only work after calling optimize_portfolio on portfolio_spec
pyPortfolioAnalysis.pyPortfolioAnalysis.factor_exposure_constraint(assets, B, lower, upper, kind='factor_exposure', enabled=True, message=False)

Add a factor exposure constraint for “K” different factos in a portdolio and also their exposure to particular asset.

assetsint, or array-like,

named list of assets specifying initial weights.

Bmatrix-like,

matrix or list of risk factor exposures

lowerint, or array-like

list of lower limits of risk factor exposure constraints.

upperint, or array-like

list of upper limits of risk factor exposure constraints.

kindstr,

string of kind of constraints.

enabledbool, default = True

bool to enable or disable constraints.

messagebool, default = False

bool to enable or disable messages.

Adds factor_exposure constraints to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

>>> #Factor_exposure constraint is used to test portfolio with their impact on certaint factors
>>> # factors can be single or multiple with lower and upper limit. 
>>> # B can be a N*K matrix for N assets and K factors.
>>> # lower and upper arguments can be float for single factor and list for multiple factors
>>> add_constraint(portfolio, kind = 'factor_exposure', 
              B = np.matrix([[1.2,1.3],
                             [2.3,1.4],
                             [1.4,0.9],
                             [3.4,1.2]]),
               lower = [0.8,1.4], upper = [2,2.4])
pyPortfolioAnalysis.pyPortfolioAnalysis.fn_map(weights, portfolio, relax=False, verbose=False)

This function transforms list of weights that does not meet the portfolio constraints to an array that meets the constraints. relax argument (default = False) if True gives the function permission to transform weights if needed

weightsarray-like,

list of initial weights.

portfolioportfolio_spec,

an object of class portfolio_spec.

relaxbool, default = False

bool to enable or disable constraints.

verbosebool, default = False

bool to enable or disable messages.

returns the array of weights tranformed by the function and that does satisfy the constraints. called by optimize_portfolio if optimize_method = ‘DEoptim’ or ‘pso’

pyPortfolioAnalysis.pyPortfolioAnalysis.generate_sequence(minimum=0.01, maximum=1.01, by=0.01, rounding=3)

The sequence of min<->max weights for random.

Creating a series of potential weights for portfolios of random or brute force.

minimumfloat,

sequence minimum value

maximumfloat,

sequence maximum value

byfloat, optional

number to increase the series by

roundingint, optional

integer the number of decimals we can round to

returns a series of ranfom weights that satisfy the min-max weights constraint. Default weight_seq for rp_transform

pyPortfolioAnalysis.pyPortfolioAnalysis.get_constraints(portfolio)

Helper functionality to get the constraints allowed out of the portfolio object

portfolioportfolio_spec,

an object of class portfolio_spec.

returns dictionary of constraints extracted from the portfolio_spec object

>>> port = portfolio_spec(3)
>>> add_constraint('dollar_neutral')
>>> get_constraint(port)
pyPortfolioAnalysis.pyPortfolioAnalysis.group_constraint(assets, groups, group_min, group_max, kind='group', enabled=True, message=False)

Group constraints determine the grouping of assets, group weights, and the number of positions of the groups (i.e. non-zero weights).

assetsInt, or array-like,

Number of assets or, as an alternative, a named asset list specifying initial weights.

groupsDict,

dictionary specifying the assets groups.

group_minfloat, or array-like,

numeric or named list defining the minimum constraints of the weight group.

group_maxfloat, or array-like,

numeric or named list defining the maximum constraints of the weight group.

kindstr,

string of kind of constraint.

enabledbool, default = True

bool to enable or disable constraints.

messagebool, default = False

bool to enable or disable messages.

Adds group constraints to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

>>> add_constraint(portfolio, kind = 'group', group_min = [0.9, -0.5,-0.5, 0.1], 
    group_max =1, groups = {'eqity':[0,3], 'debt':[1,2]})
pyPortfolioAnalysis.pyPortfolioAnalysis.group_fail(weights, groups=None, cLO=None, cUP=None, group_pos=None)

The role loops through each group and checks if the cLO or cUP for the given group has been breached. This is a rp_transform helper feature. Test if group limits have been breached.

weightsarray-like,

test the list of weights

groupsdict,

A dictionary defining the asset classes. similar in group_constraint.

cLOfloat, or array-like,

Specifying minimum weight group constraints by numeric or vector.

cUPfloat, or array-like,

Specifying maximum weight group constraints by numeric or vector.

group_posarray-like, optional

A list that defines the number of non-zero weights for each category.

Bool returning “True” if group weights are breached

pyPortfolioAnalysis.pyPortfolioAnalysis.inverse_volatility_weights(R, portfoio, **kwargs)

Function to calculate objective_measure of inverse volatility portfolio

Rpd.DataFrame,

dataframe of returns of assets in portfolio

portfolioportfolio_spec,

an object of class portfolio_spec.

kwargsadditional arguments, optional

any additional argument to be passed.

dictionary of objective measures of inverse volatility portfolio

equal_weight inverse_volatility_weight

>>> inverse_volatility_weight(R, portfolio)
pyPortfolioAnalysis.pyPortfolioAnalysis.leverage_exposure_constraint(assets, leverage, kind='leverage_exposure', enabled=True, message=True)

A maximum leverage where leverage is stated as the total of the absolute value of the weights is determined under the leverage_exposure constraint.

assetsint, or array-like,

leverage : maximum leverage value

kindstr,

string of kind of constraints

enabledbool, default = True

bool to enable or disable constraints.

messagebool, default = True

bool to enable or disable messages.

Adds leverage_exposure constraints to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

>>> #constraint on the leverage of portfolio
>>> add_constraint(portfolio, kind = 'leverage_exposure', leverage = 0.8)
pyPortfolioAnalysis.pyPortfolioAnalysis.leverage_fail(weights, leverage=None)

It is used by rp_transform as a helper function to test if leverage constraint is breached.

weightsarray-like,

test the list of weights.

leveragefloat,

specify the leverage the portfolio must satisfy

Returns “True” if the weights fail the leverage_exposure constraint. Called by rp_transform. see rp_transform.

pos_limit_fail

import numpy as np

import pandas as pd

rp_transform

pyPortfolioAnalysis.pyPortfolioAnalysis.max_sum_fail(weights, max_sum=None)

it is used by rp_transform as a helper function to test if max_sum constraint is breached.

weightsarray-like,

test the list of weights

max_sumfloat, optional

max_sum of the weights of portfolio

Returns “True” if the weights fail the max_sum constraint. Called by rp_transform. see rp_transform.

fn_map, rp_transform

pyPortfolioAnalysis.pyPortfolioAnalysis.min_sum_fail(weights, min_sum=None)

it is used by rp_transform as a helper function to test if min_sum constraint is breached.

weightsarray-like,

test the list of weights

min_sumfloat, optional

max_sum of the weights of portfolio

Returns “True” if the weights fail the min_sum constraint. Called by rp_transform. see rp_transform.

fn_map, rp_transform

pyPortfolioAnalysis.pyPortfolioAnalysis.minmax_objective(name, minimum, maximum, multiplier=1, arguments=None, target=None, enabled=True)

This target allows to determine min and max goals. Constructor for the tmp_minmax_objective.

namestr,

The target name should correspond to a feature, although we will attempt to make allowances.

minimumfloat,

minimum value

maximumfloat,

maximum value

multiplierint, optional

Multiplier to be added to the target, typically 1 or -1.

argumentsdict,

Default arguments to be transferred when executed on an objective function.

targetfloat,

Univariate goal for the target.

enabledbool, default = True

bool to enable or disable constraints.

Adds minmax_objective to object portfolio_spec of the specified input.

add_objectives portfolio_risk_objectives risk_budget_objective turnover_objective minmax_objective weight_constraint_objective

>>> port = portfolio_spec(assets = 5)
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> add_constraint('long_only')
>>> add_constraint('full_investment')
>>> #adding objectives
>>> add_objective(kind = 'risk', name = 'std', target = 0.015)
NOTE: you can add other custom function in other kind of objective in similar methd. See add_objective
pyPortfolioAnalysis.pyPortfolioAnalysis.normalize_weights(weights)

Add a constraint in portfolio_spec object

Main function to add or update constraint in portfolio_spec object

weightsarray-like,

list of weights to normalize based on constraints.

Returns array of normalized weights. Called be optimize_portfolio when optimize_method is: ‘pso’, ‘dual_annealing’, ‘shgo’, ‘basinhopping’, ‘brute’.

pyPortfolioAnalysis.pyPortfolioAnalysis.optimize_portfolio(R, portfolio=None, constraints=None, objectives=None, optimize_method=['pso', 'DEoptim', 'dual_annealing', 'brute', 'shgo', 'basinhopping', 'best'], search_size=20000, trace=False, message=False, **kwargs)

This function is calls the portfolio to optimize the weights given the constrained and objectives of portfolio provided using add_constraint and add_objective functions.

Main function to optimize portfolio weights given the constraints and objectives

Rpandas dataframe,

dataframe of the series of returns

portfolioportfolio_spec,

an object of class portfolio_spec.

constraintsdict, optional

constraints to be minimized/maximized given the assets. Although they are automatically called if portfolio_spec object has constraints specified

objectivesdict, optional

objectives to be minimized/maximized given the assets. Although they are automatically called if portfolio_spec object has objectives specified

optimize_methodfloat,

the method for optimizing portfolio. currently supported methods are: ‘pso’ ‘DEoptim’ ‘dual_annealing’ ‘brute’ ‘shgo’ ‘basinhopping’

User can also specify ‘best’ as optimize_method to use all optimizer and choose the best among them.

search_size: int, optional

specify th iterations to do before calling the best portfolio

tracebool, default = False

bool to enable or disable trace of portfolio.

messagebool, default = False

bool to enable or disable messages.

kwargsadditional key word arguments, optional

any additional constraint argument to be passed.

returns the optimal weights, objective measure, value of the best optimization (out). automatically adds weights to the portfolio_spec objects.

portfolio_spec add_constraint add_objective

currently suuported optimization methods are:

‘pso’ ‘DEoptim’ ‘dual_annealing’ ‘brute’ ‘shgo’ ‘basinhopping’

The function calls constrained_objective to minimize the penalty (default = 10000) to come to a solution. the purpose of adding different optimization method is to give flexibility to user to choose optimizer based on specific problem.

Additional arguments can be specified such as maxiter, disp and other controls. the argument names are similar in scipy.optimize.[optimizer] or pyswarms. see scipy and pyswarm documentation.

>>> port = portfolio_spec(assets = 5)
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> add_constraint('long_only')
>>> add_constraint('full_investment')
>>> #adding objectives
>>> add_objective(kind = 'return', name = 'mean', target = 0.0018)
>>> add_objective(kind = 'portfolio_risk', name = 'std', target = 0.015)
>>> add_objective(kind = 'risk_budget', name = 'risk_budget')
>>> add_objective(kind = 'weight_conc', name = 'HHI', target = 0.11)
>>> add_objective(kind = 'performance_metrics', name = 'sharpe', target = 0.13)
>>> # add a custom objective by first defining it.
>>> def sortino_ratio(w,R):
        #SOME CODE
>>> add_objective(kind = 'performance_metrics', name = {'sortino':sortino_ratio}, target = 0.35)
NOTE: The output of sortino_ratio or other custom function in objective must be a float.
NOTE: you can also add other custom function in other kind of objective in similar methd.
>>> optimize_portfolio(R, port, optimize_method  = 'DEoptim', disp = False, search_size = 30000)
NOTE: Yout can provide addional adguments based on solver. See the solver documentation for more information.
>>> # we have used scipy.optimize for most of the solver and pyswarms for 'pso' method.
>>> optimize_portfolio(R, port, optimize_method  = 'best', disp = False, maxiter = 1000)
NOTE: 'best' optimize_method takes a while to give ouput because it uses all other optimizers.
pyPortfolioAnalysis.pyPortfolioAnalysis.performance_metrics_objective(name, arguments, target=None, multiplier=1, enabled=True)

We’ll try minimizing the performance_metric if the target is null. Constructor for the portfolio_risk_objective class.

namestr,

The target name should correspond to a feature, although we will attempt to make allowances

targetfloat,

Univariate goal for the target.

argumentsdict, optional

Default arguments to be transferred when executed on an objective function.

multiplierint, optional

Multiplier to be added to the target, typically 1 or -1.

enabledbool, default = True

bool to enable or disable constraints.

Adds portfolio risk objectives to object portfolio_spec of the specified input.

add_objectives portfolio_risk_objectives risk_budget_objective turnover_objective minmax_objective weight_constraint_objective

>>> port = portfolio_spec(assets = 5)
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> add_constraint('long_only')
>>> add_constraint('full_investment')
>>> #adding objectives
>>> add_objective(kind = 'performance_metrics', name = 'sharpe', target = 0.13)
>>> # add a custom objective by first defining it.
>>> def sortino_ratio(w,R):
        #SOME CODE
>>> add_objective(kind = 'performance_metrics', name = {'sortino':sortino_ratio}, target = 0.35)
NOTE: The output of sortino_ratio or other custom function in objective must be a float.
NOTE: you can also add other custom function in other kind of objective in similar methd.
pyPortfolioAnalysis.pyPortfolioAnalysis.port_mean(weights, mu)

Add a constraint in portfolio_spec object Main function to add or update constraint in portfolio_spec object

weightsarray-like,

weights of the portfolio.

muarray-like,

mean return of assets

Adds port mean to object portfolio_spec of the specified input.

mu_{p} = w . mu_{r}

var_portfolio VaR cVaR

>>> #calculate the portfolio mean return
>>> w = [0.2,0.3,-0.1,0.6,0.8]
>>> port_mean(w,R)
pyPortfolioAnalysis.pyPortfolioAnalysis.portfolio_risk_objective(name, target, arguments, multiplier=- 1, enabled=True)

We’ll try minimizing the risk metric if the target is null. Constructor for the portfolio_risk_objective class.

namestr,

The target name should correspond to a feature, although we will attempt to make allowances

targetfloat,

Univariate goal for the target.

argumentsdict, optional

Default arguments to be transferred when executed on an objective function.

multiplierint, optional

Multiplier to be added to the target, typically 1 or -1.

enabledbool, default = True

bool to enable or disable constraints.

Adds portfolio risk objectives to object portfolio_spec of the specified input.

add_objectives portfolio_risk_objectives risk_budget_objective turnover_objective minmax_objective weight_constraint_objective

>>> port = portfolio_spec(assets = 5)
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> add_constraint('long_only')
>>> add_constraint('full_investment')
>>> #adding objectives
>>> add_objective(kind = 'portfolio_risk', name = 'std', target = 0.015)
>>> # add a custom objective by first defining it.
>>> def sortino_ratio(w,R):
        #SOME CODE
>>> add_objective(kind = 'performance_metrics', name = {'sortino':sortino_ratio}, target = 0.35)
NOTE: The output of sortino_ratio or other custom function in objective must be a float.
NOTE: you can also add other custom function in other kind of objective in similar methd.
class pyPortfolioAnalysis.pyPortfolioAnalysis.portfolio_spec(assets, category_labels=None, weights_seq=None, message=False)

Bases: object

A class to call portfolio_spec object.

portfolio_spec object is the main class that contains all the constraints, objectives, optimal weights; it is called by many functions to get relevant attributes and store attributes.

assetsint, or array-like,

add assets to portfolio either via name of assets in the form of an array or int of number of assets.

category_label: dict, optional

dictionary of different categories assigned to different assets. similar to group_constraint. See group_constraint.

weights_seqsequence, optional

sequence of random weights. These weights will be used to optimize weights. See generate_sequence

messagebool, default = False

bool to enable or diable message

port_summary():

returns a dictionary of the summary of constraints and objective added by add_consraint and add_objective funtions. See add_constraint, add_objective

optimal_portfolio():

returns a dictionary of optimal weights, objective measure and minimum value calculated by the specified solver NOTE: optimal_portfolio will only return result if optimize_portfolio is called. See optimize_portfolio

optimal_portfolio()

summary of the portfolio

method to provide a summary of the optimal weights, objective and minimum output of portfolio.

dict:

returns a dictionary of optimal weights, objective and minimum output of portfolio

portfolio_spec optimize_portfolio

>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> p1 = portfolio_spec(assets = 3)
>>> add_constraint(portfolio = p1, kind = 'factor_exposure', B = [0.2,0.2,0.4], lower = 1.0, upper = 0.9)
>>> add_constraint(portfolio = p1, kind = 'group', groups = dict(zip(['equity','debt'],[[0,1], [2]])), group_min = 0.2, group_max = 0.5)
>>> add_constraint(portfolio = p1, kind = 'transaction', ptc = 0.2)
>>> add_objective(portfolio = p1, kind = 'return', target = 0.1, name = 'return_obj')
>>> add_objective(portfolio = p1, kind = 'minmax',  minimum = 0.2, maximum = 0.3,name = 'risk')
>>> optimize_portfolio(R, p1, optimize_method = 'DEoptim')
>>> p1.optimal_weights()
port_summary()

summary of the portfolio

method to provide a summary of the portfolio.

dict:

returns a dictionary of all constraints and objective

portfolio_spec optimize_portfolio

>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> p1 = portfolio_spec(assets = 3)
>>> add_constraint(portfolio = p1, kind = 'factor_exposure', B = [0.2,0.2,0.4], lower = 1.0, upper = 0.9)
>>> add_constraint(portfolio = p1, kind = 'group', groups = dict(zip(['equity','debt'],[[0,1], [2]])), group_min = 0.2, group_max = 0.5)
>>> add_constraint(portfolio = p1, kind = 'transaction', ptc = 0.2)
>>> add_objective(portfolio = p1, kind = 'return', target = 0.1, name = 'return_obj')
>>> add_objective(portfolio = p1, kind = 'minmax',  minimum = 0.2, maximum = 0.3,name = 'risk')
>>> p1.port_summary()
pyPortfolioAnalysis.pyPortfolioAnalysis.pos_limit_fail(weights, max_pos=None, max_pos_long=None, max_pos_short=None)

This is used as a rp_transform helper function to search for position limit constraints being violated.

weightsarray-like,

test list of weights.

max_posint, optional

maximum number of non-zero-weighted assets

max_pos_longint, optional

maximum number of long-position assets

max_pos_shortint, optional

maximum number of short-position assets

Returns “True” if the weights fail the pos_limit constraint. called by rp_transform. see rp_transform.

pyPortfolioAnalysis.pyPortfolioAnalysis.position_limit_constraint(assets, max_pos=None, kind='position', max_pos_long=None, max_pos_short=None, enabled=True, message=True)

When type=”position_limit” is mentioned, this function is called by add.constraint.

The maximum number of positions as well as the maximum number of long and short positions are determined by the user using this function.

assetsint, or array-like,

named list of assets determining initial weights.

max_posint,

maximum number of assets with non-zero weights.

kindstr,

string of kind of constraint

max_pos_longInt, optional

maximum number of assets with long positions.

max_pos_shortInt, optional

maximum number of assets with short positions.

enabledbool, default = True

bool to enable or disable constraints.

messagebool, default = True

bool to enable or disable messages.

Adds position_limit constraints to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

>>> #position_limit is a constraint to restrict max position and also max long/short positions
>>> add_constraint(portfolio, kind = 'position_limit', max_pos = 3, max_pos_long = 2, max_pos_short = 2)
pyPortfolioAnalysis.pyPortfolioAnalysis.return_constraint(assets, return_target, kind='return', enabled=True, message=False)

Target mean return value is determined by the return constraint. When type=”return” is mentioned, this function is called by add_constraint.

assets :. int, or array-like,

named list of assets determining initial weights.

kindstr,

string of kind of constraints.

enabledbool, default = True

bool to enable or disable constraints.

messagesbool, default = False

bool to enable or disable messages.

Adds return constraints to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

>>> #return constraint to add a target mean historical return to the portfolio
>>> add_constraint(portfolio, kind = 'return', return_target = 0.0018)
pyPortfolioAnalysis.pyPortfolioAnalysis.return_objective(name, target, arguments, multiplier=- 1, enabled=True)

We’ll try minimizing the risk metric if the target is null. Constructor for the portfolio_risk_objective class.

namestr,

The target name should correspond to a feature, although we will attempt to make allowances

targetfloat,

Univariate goal for the target.

argumentsdict, optional

Default arguments to be transferred when executed on an objective function.

multiplierint, optional

Multiplier to be added to the target, typically 1 or -1.

enabledbool, default = True

bool to enable or disable constraints.

Adds return_objective to object portfolio_spec of the specified input.

add_objectives portfolio_risk_objectives risk_budget_objective turnover_objective minmax_objective weight_constraint_objective

>>> port = portfolio_spec(assets = 5)
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> add_constraint('long_only')
>>> add_constraint('full_investment')
>>> #adding objectives
>>> add_objective(kind = 'return', name = 'mean', target = 0.0018)
>>> # add a custom objective by first defining it.
>>> def sortino_ratio(w,R):
        #SOME CODE
>>> add_objective(kind = 'performance_metrics', name = {'sortino':sortino_ratio}, target = 0.35)
NOTE: The output of sortino_ratio or other custom function in objective must be a float.
NOTE: you can also add other custom function in other kind of objective in similar methd.
pyPortfolioAnalysis.pyPortfolioAnalysis.risk_budget_objective(assets, name, min_prisk=None, max_prisk=None, target=None, arguments=None, multiplier=1, enabled=True, min_concentration=False, min_difference=False)

Constructor for the risk_budget_objective.

assetsint, or array-like,

The asset list to be used should come from object constraints.

namestr,

The target name should correspond to a feature, although we will attempt to make allowances.

min_priskfloat,

minimum percentage risk contribution

max_priskfloat,

maximum percentage risk contribution

argumentsdict, optional

Default arguments to be transferred when executed on an objective function.

multiplierint, optional

Multiplier to be added to the target, typically 1 or -1.

Adds risk budget objective to object portfolio_spec of the specified input.

add_objectives portfolio_risk_objectives risk_budget_objective turnover_objective minmax_objective weight_constraint_objective

Examples
>>> port = portfolio_spec(assets = 5)
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> add_constraint('long_only')
>>> add_constraint('full_investment')
>>> #adding objectives
>>> add_objective(kind = 'risk_budget', name = 'risk_budget')
>>> add_objective(kind = 'weight_conc', name = 'HHI', target = 0.11)
>>> add_objective(kind = 'performance_metrics', name = 'sharpe', target = 0.13)
>>> # add a custom objective by first defining it.
>>> def sortino_ratio(w,R):
        #SOME CODE
>>> add_objective(kind = 'performance_metrics', name = {'sortino':sortino_ratio}, target = 0.35)
NOTE: The output of sortino_ratio or other custom function in objective must be a float.
NOTE: you can also add other custom function in other kind of objective in similar methd.
pyPortfolioAnalysis.pyPortfolioAnalysis.rp_decrease(weights, max_sum, min_box, weight_seq)

It is used by rp_transform as a helper function to reduce weights if max_sum or min_box constraint is breached.

weightsarray-like,

test of list of weights

max_sumfloat,

maximum sum of weights

min_boxarray-like,

minimum of individual weights in a portfolio

weight_seqseq,

sequence of random weights to choose from

returns an array of weights that satisfy the max_sum and min_box constraint. called by rp_transform.

rp_increase rp_transform

pyPortfolioAnalysis.pyPortfolioAnalysis.rp_decrease_leverage(weights, max_box, min_box, leverage, weight_seq)

It is used by rp_transform as a helper function to redcrese leverage if leverage_exposure constraint is breached.

weightsarray-like,

test of list of weights

max_boxarray-like,

maximum of individual weights in a portfolio

min_boxlike,

minimum of individual weights in a portfolio

leverage: float,

leverage as specified in leverage_exposure constraints

weight_seqseq,

sequence of random weights to choose from

returns an array of weights that satisfy the leverage constraint. called by rp_transform.

rp_increase rp_transform

pyPortfolioAnalysis.pyPortfolioAnalysis.rp_increase(weights, min_sum, max_box, weight_seq)

It is used by rp_transform as a helper function to increase weights if min_sum or max_box constraint is breached.

weightsarray-like,

test of list of weights

max_sumfloat,

maximum sum of weights

min_boxfloat,

minimum of individual weights in a portfolio

weight_seqseq,

sequence of random weights to choose from

returns an array of weights that satisfy the max_sum and min_box constraint. called by rp_transform.

rp_increase rp_transform

pyPortfolioAnalysis.pyPortfolioAnalysis.rp_position_limit(weights, min_box, max_box, weight_seq, max_pos=None, max_pos_long=None, max_pos_short=None)

It is used by rp_transform as a helper function to increase weights if position_limit constraint is breached.

weightsarray-like,

test of list of weights

min_boxarray-like,

maximum of individual weights in a portfolio

min_boxarray-like,

minimum of individual weights in a portfolio

max_posint, optional

maximum position to hold in a portfolio

max_pos_longint, optional

maximum long position to hold in a portfolio

max_pos_shortint, optional

maximum short position to hold in a portfolio

weight_seqseq,

sequence of random weights to choose from

returns an array of weights that satisfy the position limit constraint. called by rp_transform.

rp_increase rp_transform rp_decrease_leverage

pyPortfolioAnalysis.pyPortfolioAnalysis.rp_transform(w, min_sum, max_sum, min_box, max_box, groups=None, cLO=None, cUP=None, group_pos=None, max_pos=None, max_pos_long=None, max_pos_short=None, leverage=None, weight_seq=None, max_permutations=2000)

This function is mainly used to transform weights that dont satisfy the constraints such as: “box” “group” “max_pos” “leverage_exposure” See add_constraint for more deatils.

Transform a list of weights to fulfill constraints

weightsarray-like,

list of weights to be transformed

min_sumfloat,

minimum total of all weights of assets, default of 0.99

max_sumfloat,

maximum total of all weights of assets, default of 1.01

min_boxarray-like,

numeric or called list defining the minimum constraints of the weight box

max_boxarray-like

numeric or called list defining the maximum constraints of the weight box

groupsdict,

a dictionary defining the asset groups. similar to group_constraint. see group_constraint

cLOflaot, or array-like,

float or list defining the minimum constraints of the weight group

cUPfloat, or array-like

float or list defining the minimum constraints of the weight group

group_posarray-like, optional

list that specifies the maximum number of non-zero-weight assets per group

max_posint,

maximum non-zero-weight assets

max_pos_longint

maximum number of long (i. e. buy) position assets

max_pos_shortint,

maximum number of short (i. e. sell) position assets

leveragefloat,

maximum exposure to leverage in which leverage is defined as sum(abs(weights))

weight_seqseq, optional

list of seed sequence of weights. uses generate_sequence()

max_permutationsint, optional

integer- maximum number of iterations to try for a portfolio which is valid, default 2000

weights array that satisfy the constraints on portfolio

rp_increase rp_decrease fn_map

pyPortfolioAnalysis.pyPortfolioAnalysis.transaction_cost_constraint(assets, ptc, kind='transaction', enabled=True, message=True)

A proportional cost value is determined under the transaction cost constraint. When type=”transaction_cost” is specified, this function is called by add.constraint.

assetsint, or array-like,

number of assets, or optionally a named list of assets determining initial weights.

ptcfloat,

proportional transaction cost value.

kindstr,

string of kind of constraint

enabledbool, default = True

bool to enable or disable constraints.

messagebool, default = True

bool to enable or disable messages.

Adds transaction _cost constraints to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

>>> #adds a tranaction cost constraint on portfolio
>>> add_constraint(portfolio, kind = 'transaction_cost', ptc = 0.1)
pyPortfolioAnalysis.pyPortfolioAnalysis.turnover(weights, wgt_init=None)

Turnover estimation of two weight lists. This is used as an objective function and is named when the user adds with add.objective an objective of type turnover.

weightsarray-like,

Weights list from optimization.

wgt_initarray-like, optional

Initial weights list used for measuring turnover from.

returns the turnover of the portfolio given the weights

var_portfolio port_mean

>>> port = portfolio_spec(assets = 5)
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> w = [0.2,0.3,0.4,-.4,0.5]
>>> turnover(w)
pyPortfolioAnalysis.pyPortfolioAnalysis.turnover_constraint(assets, turnover_target, kind='turnover', enabled=True, message=True)

Target turnover value is determined under the turnover constraint. When type=”turnover” is stated, the function is called by add.constraint

assetInt, or array-like,

Number of assets or, as an alternative, a named asset list specifying initial weights.

kindstr,

character kind of the constraint.

enabledbool, default = True

bool to enable or disable constraints.

messagebool, default = True

bool to enable or disable messages.

Adds turnover constraints to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

>>> #turnover constraint
>>> add_constraint(portfolio, kind = 'turnover', turnover_target = 0.1)
pyPortfolioAnalysis.pyPortfolioAnalysis.turnover_objective(name, arguments, target=None, multiplier=1, enabled=True)

We’ll try minimizing the turnover metric if the goal is null. Constructor for the turnover_objective class.

namestr,

The target name should correspond to a feature, although we will attempt to make allowances.

argumentsdict,

Default arguments to be transferred when executed on an objective function.

targetfloat,

Univariate goal for the target.

multiplierint, optional

Multiplier to be added to the target, typically 1 or -1.

enabledbool, default = True

bool to enable or disable constraints.

Adds turnover_objective to object portfolio_spec of the specified input.

add_objectives portfolio_risk_objectives risk_budget_objective turnover_objective minmax_objective weight_constraint_objective

>>> port = portfolio_spec(assets = 5)
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> add_constraint('long_only')
>>> add_constraint('full_investment')
>>> #adding objectives
>>> 
>>> add_objective(kind = 'turnover', name = 'turnover', target = 0.2)
>>> add_objective(kind = 'performance_metrics', name = 'sharpe', target = 0.13)
>>> # add a custom objective by first defining it.
>>> def sortino_ratio(w,R):
        #SOME CODE
>>> add_objective(kind = 'performance_metrics', name = {'sortino':sortino_ratio}, target = 0.35)
NOTE: The output of sortino_ratio or other custom function in objective must be a float.
NOTE: you can also add other custom function in other kind of objective in similar methd.
pyPortfolioAnalysis.pyPortfolioAnalysis.var_portfolio(R, weights)

When var is an object for mean variance or quadratic utility optimization, this function is used to measure the portfolio variance through a call to constrained_objective.

Main function to calculate portfolio variance

Rpd.DataFrame,

return series

weights: array-like,

list of weights of assets.

returns the variance of the portfolio given the following weights.

sigma_{p} = w Sigma_{p} w^{T}

port_mean VaR cVaR

>>> # calculate the variance of portfolio
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> w = [0.2,0.3,-0.1,0.6,0.8]
>>> var_portfolio(w,R)
pyPortfolioAnalysis.pyPortfolioAnalysis.weight_concentration_objective(name, conc_aversion, conc_groups=None, multiplier=1, arguments=None, enabled=True)

Using the HHI as a concentration scale, this feature penalizes weight concentration Constructor for objective of weight concentration.

namestr,

The name of the concentration measure is currently only supported by “HHI”.

conc_aversionfloat,

concentration value(s) of aversion

conc_groupsdict,

A dictionary defining the asset classes. Similar to ‘group constraint’ groups.

multiplierint, optional

Multiplier to be added to the target, typically 1 or -1.

argumentsdict, optional

Default arguments to be transferred when executed on an objective function.

enabledbool, default = True

bool to enable or disable constraints.

Adds weight constraints objective to object portfolio_spec of the specified input.

add_objectives portfolio_risk_objectives risk_budget_objective turnover_objective minmax_objective weight_constraint_objective

>>> port = portfolio_spec(assets = 5)
>>> import pandas_datareader as pdr
>>> aapl = pdr.get_data_yahoo('AAPL')
>>> msft = pdr.get_data_yahoo('MSFT')
>>> tsla = pdr.get_data_yahoo('TSLA')
>>> uber = pdr.get_data_yahoo('UBER')
>>> amzn = pdr.get_data_yahoo('AMZN')
>>> port = pd.DataFrame({'aapl': pd.DataFrame.reset_index(aapl).iloc[:,6], 'msft':pd.DataFrame.reset_index(msft).iloc[:,6],
    'tsla': pd.DataFrame.reset_index(tsla).iloc[:,6], 'uber':pd.DataFrame.reset_index(uber).iloc[:,6],
    'amzn': pd.DataFrame.reset_index(amzn).iloc[:,6]})
>>> port_ret = port.pct_change().dropna()
>>> R = port_ret
>>> add_constraint('long_only')
>>> add_constraint('full_investment')
>>> add_objective(kind = 'weight_conc', name = 'HHI', target = 0.11)
>>> add_objective(kind = 'performance_metrics', name = 'sharpe', target = 0.13)
>>> # add a custom objective by first defining it.
>>> def sortino_ratio(w,R):
        #SOME CODE
>>> add_objective(kind = 'performance_metrics', name = {'sortino':sortino_ratio}, target = 0.35)
NOTE: The output of sortino_ratio or other custom function in objective must be a float.
NOTE: you can also add other custom function in other kind of objective in similar methd.
pyPortfolioAnalysis.pyPortfolioAnalysis.weight_sum_constraint(assets, kind='weight_sum', min_sum=0.99, max_sum=1.01, enabled=True, message=True)

The constraint determines the sum of the weights of the upper and lower limits. This function is called add.constraint when the type is defined as “weight sum”, “leverage”, “full investment”, “dollar neutral” or “active”

assetsInt, or array-like,

Number of assets or, as an alternative, a named asset list specifying initial weights.

kindstr,

character kind of the constraint.

min_sumfloat,

Minimum sum of all weights of assets, default 0.99

max_sumfloat,

Maximum sum of all weights of assets, default 1.01

enabledbool, default = True

bool to enable or disable constraints.

messagebool, default = True

bool to enable or disable messages.

Adds weight_sum constraint to object portfolio_spec of the specified input.

add_constraints box_constraints group_constraints weight_sum_constraint turnover_constraint diversification_constraint position_limit_constraint return_constraint factor_exposure_constraint transaction_cost_constraint leverage_exposure_constraint

>>> # adding weight_sum constraint
>>> add_constraint(portfolio, kind = 'weight_sum', min_sum = 0.9, max_sum = .95)
>>> # special case of weight_sum is dollar_neutral/active or full_investment
>>> add_constraint(portfolio, kind = 'dollar_neutral')
>>> add_constraint(portfolio, kind = 'full_investment')

Module contents

pyPortfolioAnalysis: Methods to optimize portfolio

Documentation is available as docstring or as HTML on https://github.com/anuragagrawaal/pyPortfolioAnalysis

Functions and Classes

Optimization Methods

‘HHI’ ‘VaR’ ‘VaR_portfolio’ ‘add_constraint’ ‘add_objective’ ‘black_litterman’ ‘box_constraint’ ‘cVaR_portfolio’ ‘constrained_objective’ ‘diversification’ ‘diversification_constraint’ ‘equal_weight’ ‘extract_groups’ ‘extract_objective_measure’ ‘extract_weights’ ‘factor_exposure_constraint’ ‘fn_map’ ‘generate_sequence’ ‘get_constraints’ ‘group_constraint’ ‘group_fail’ ‘inverse_volatility_weights’ ‘leverage_exposure_constraint’ ‘leverage_fail’ ‘max_sum_fail’ ‘min_sum_fail’ ‘minmax_objective’ ‘normalize_weights’ ‘optimize_portfolio’ ‘performance_metrics_objective ‘port_mean’ ‘portfolio_risk_objective’ ‘portfolio_spec’ ‘pos_limit_fail’ ‘position_limit_constraint’ ‘return_constraint’ ‘return_objective’ ‘risk_budget_objective’ ‘rp_decrease’ ‘rp_decrease_leverage’ ‘rp_increase’ ‘rp_position_limit’ ‘rp_transform’ ‘transaction_cost_constraint’ ‘turnover’ ‘turnover_constraint’ ‘turnover_objective’ ‘var_portfolio’ ‘weight_concentration_objective’ ‘weight_sum_constraint’

Plots

‘chart_efficient_frontier’ ‘chart_group_weights’ ‘chart_weights’

References

Brian G. Peterson and Peter Carl (2018). PortfolioAnalytics: Portfolio Analysis, Including Numerical Methods for Optimization of Portfolios. R package version 1.1.0. https://CRAN.R-project.org/package=PortfolioAnalytics

Boudt, Kris and Lu, Wanbo and Peeters, Benedict, Higher Order Comoments of Multifactor Models and Asset Allocation (June 16, 2014). Available at SSRN: http://ssrn.com/abstract=2409603 or http://dx.doi.org/10.2139/ssrn.2409603

Chriss, Neil A and Almgren, Robert, Portfolios from Sorts (April 27, 2005). Available at SSRN: http://ssrn.com/abstract=720041 or http://dx.doi.org/10.2139/ssrn.720041

Meucci, Attilio, The Black-Litterman Approach: Original Model and Extensions (August 1, 2008). Shorter version in, THE ENCYCLOPEDIA OF QUANTITATIVE FINANCE, Wiley, 2010. Avail- able at SSRN: http://ssrn.com/abstract=1117574 or http://dx.doi.org/10.2139/ssrn.1117574

Meucci, Attilio, Fully Flexible Views: Theory and Practice (August 8, 2008). Fully Flexible Views: Theory and Practice, Risk, Vol. 21, No. 10, pp. 97-102, October 2008. Available at SSRN: http://ssrn.com/abstract=1213325

Scherer, Bernd and Martin, Doug, Modern Portfolio Optimization. Springer. 2005.

Shaw, William Thornton, Portfolio Optimization for VAR, CVaR, Omega and Utility with General Return Distributions: A Monte Carlo Approach for Long-Only and Bounded Short Portfolios with Optional Robustness and a Simplified Approach to Covariance Matching (June 1, 2011). Available at SSRN: http://ssrn.com/abstract=1856476 or http://dx.doi.org/10.2139/ssrn.1856476