def test_ledoit_wolf_cor_forecast_days(): sigma, average_cor, shrink = ledoit_wolf.ledoit_wolf_cor( ("MSRS", "MTSS", "PLZL"), pd.Timestamp("2021-09-30"), 30, ) sigma2, average_cor2, shrink2 = ledoit_wolf.ledoit_wolf_cor( ("MSRS", "MTSS", "PLZL"), pd.Timestamp("2021-10-01"), 30, 1, ) assert np.allclose(sigma, sigma2) assert average_cor == average_cor2 assert shrink == shrink2
def _opt_weight( mean: np.array, variance: np.array, tickers: tuple[str], end: pd.Timestamp, phenotype: PhenotypeData, ) -> tuple[np.array, np.array]: """Веса портфеля с максимальными темпами роста и использовавшаяся ковариационная матрица. Задача максимизации темпов роста портфеля сводится к максимизации математического ожидания логарифма доходности. Дополнительно накладывается ограничение на полною отсутствие кэша и неотрицательные веса отдельных активов. """ history_days = phenotype["data"]["history_days"] mean = mean.reshape(-1, 1) sigma = ledoit_wolf.ledoit_wolf_cor(tickers, end, history_days, config.FORECAST_DAYS)[0] std = variance**0.5 sigma = std.reshape(1, -1) * sigma * std.reshape(-1, 1) w = np.ones_like(mean).flatten() rez = optimize.minimize( _make_utility_func(phenotype, mean, sigma), w, bounds=[(0, None) for _ in w], ) return rez.x / rez.x.sum(), sigma
def test_ledoit_wolf_cor(): cor, average_cor, shrink = ledoit_wolf.ledoit_wolf_cor( ("GAZP", "MTSS", "PLZL"), pd.Timestamp("2020-05-19"), 31, ) assert cor.shape == (3, 3) assert np.allclose(cor, cor.transpose()) assert np.allclose(np.diag(cor), 1) assert np.allclose(average_cor, 0.3451296876579886) assert np.allclose(average_cor, (cor.sum() - 3) / 6) assert np.allclose(shrink, 0.5643370267153482)
def test_ledoit_wolf_cor(): cor, average_cor, shrink = ledoit_wolf.ledoit_wolf_cor( ("CHEP", "MTSS", "PLZL"), pd.Timestamp("2020-05-19"), 31, ) assert cor.shape == (3, 3) assert np.allclose(cor, cor.transpose()) assert np.allclose(np.diag(cor), 1) assert np.allclose(average_cor, 0.3009843442553877) assert np.allclose(average_cor, (cor.sum() - 3) / 6) assert np.allclose(shrink, 0.8625220790109036)
def _opt_weight( mean: np.array, variance: np.array, tickers: tuple[str], end: pd.Timestamp, phenotype: PhenotypeData, ) -> tuple[np.array, np.array]: """Веса портфеля с максимальными темпами роста и использовавшаяся ковариационная матрица. Задача максимизации темпов роста портфеля сводится к максимизации математического ожидания логарифма доходности. Дополнительно накладывается ограничение на полною отсутствие кэша и неотрицательные веса отдельных активов. """ history_days = phenotype["data"]["history_days"] mean = mean.reshape(-1, 1) sigma = ledoit_wolf.ledoit_wolf_cor(tickers, end, history_days, config.FORECAST_DAYS)[0] std = variance**0.5 sigma = std.reshape(1, -1) * sigma * std.reshape(-1, 1) w = np.ones_like(mean).flatten() rez = optimize.minimize( lambda x: -(x.reshape(1, -1) @ mean).item(), w, jac=lambda x: -mean.flatten(), method="SLSQP", bounds=[(0, None) for _ in w], constraints=[ { "type": "eq", "fun": lambda x: x.sum() - 1, "jac": lambda x: np.ones_like(x), }, { "type": "ineq", "fun": lambda x: phenotype["utility"]["max_std"] ** 2 - (x.reshape(1, -1) @ sigma @ x.reshape(-1, 1)).item(), "jac": lambda x: (-2 * sigma @ x.reshape(-1, 1)).flatten(), }, ], ) return rez.x / rez.x.sum(), sigma
def test_forecast(): data = forecast.Forecast( tickers=TICKERS, date=DATE, history_days=30, mean=MEAN, std=STD, max_std=1.1, ) assert data.cov.shape == (3, 3) assert np.allclose(np.diag(data.cov), STD.values**2) assert np.allclose(data.cov, data.cov.transpose()) cor, *_ = ledoit_wolf.ledoit_wolf_cor(TICKERS, DATE, HISTORY_DAYS) assert np.allclose( cor, data.cov / STD.values.reshape(1, -1) / STD.values.reshape(-1, 1)) assert np.allclose(data.cor, 0.1605639317251608) assert np.allclose(data.shrinkage, 1)
def test_forecast(): data = forecast.Forecast( tickers=TICKERS, date=DATE, history_days=30, mean=MEAN, std=STD, risk_aversion=1.1, error_tolerance=0.2, ) assert data.cov.shape == (3, 3) assert np.allclose(np.diag(data.cov), STD.values**2) assert np.allclose(data.cov, data.cov.transpose()) cor, *_ = ledoit_wolf.ledoit_wolf_cor(TICKERS, DATE, HISTORY_DAYS) assert np.allclose( cor, data.cov / STD.values.reshape(1, -1) / STD.values.reshape(-1, 1)) assert np.allclose(data.cor, 0.1579351254545552) assert np.allclose(data.shrinkage, 0.7074063618114778)
def __post_init__(self): sigma, self.cor, self.shrinkage = ledoit_wolf_cor( self.tickers, self.date, self.history_days) std = self.std.values self.cov = std.reshape(1, -1) * sigma * std.reshape(-1, 1)