class Beta(CustomFactor): outputs = ['beta', 'residual_var'] inputs = [DailyReturns(), DailyReturns()[symbol('SPY')]] window_length = 252 params = ('standardize',) def compute(self, today, assets, out, assets_returns, market_returns, standardize): allowed_missing_percentage = 0.25 allowed_missing_count = int(allowed_missing_percentage * self.window_length) (out.beta, out.residual_var) = beta_residual(assets_returns, market_returns, allowed_missing_count, standardize)
class MarketDispersion(CustomFactor): inputs = [DailyReturns()] window_length = 1 window_safe = True def compute(self, today, assets, out, returns): # returns are days in rows, assets across columns out[:] = np.sqrt(np.nanmean((returns - np.nanmean(returns))**2))
class MarketVolatility(CustomFactor): inputs = [DailyReturns()] window_length = 1 window_safe = True def compute(self, today, assets, out, returns): mkt_returns = np.nanmean(returns, axis=1) out[:] = np.sqrt(260. * np.nanmean( (mkt_returns - np.nanmean(mkt_returns))**2))
class MarketVolatility(CustomFactor): inputs = [DailyReturns()] window_length = 1 # We'll want to set this in the constructor when creating the object. window_safe = True def compute(self, today, assets, out, returns): DAILY_TO_ANNUAL_SCALAR = 252. # 252 trading days in a year """ For each row (each row represents one day of returns), calculate the average of the cross-section of stock returns So that market_returns has one value for each day in the window_length So choose the appropriate axis (please see hints above) """ mkt_returns = np.nanmean(returns, axis=1) """ Calculate the mean of market returns """ mkt_returns_mu = np.nanmean(mkt_returns) """ Calculate the standard deviation of the market returns, then annualize them. """ out[:] = np.sqrt(DAILY_TO_ANNUAL_SCALAR * np.nanmean( (mkt_returns - mkt_returns_mu)**2))
def test_daily_returns_is_special_case_of_returns(self): self.check_equivalent_terms({ 'daily': DailyReturns(), 'manual_daily': Returns(window_length=2), })