Commit 1dd35635 authored by Dr.李's avatar Dr.李

initial commit

parents
.ipynb_checkpoints
__pycache__
\ No newline at end of file
{
"cells": [
{
"cell_type": "markdown",
"metadata": {},
"source": [
"> 在这个notebook中,我们测试UQER与TF的风险模型方差解释度"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"%matplotlib inline\n",
"import numpy as np\n",
"import pandas as pd\n",
"from tf.CovCal import RiskMatrics\n",
"from tf.CovCal import BarraCov\n",
"from PyFin.api import advanceDateByCalendar"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## 0. Data Preparation\n",
"------------------"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"risk_cov = pd.read_parquet('data/risk_cov.parqut').sort_values(['trade_date', 'FactorID']).set_index('trade_date')\n",
"risk_exp = pd.read_parquet('data/risk_exposure.parqut').sort_values(['trade_date', 'code']).set_index('trade_date')\n",
"specific_risk = pd.read_parquet('data/special_risk.parqut').sort_values(['trade_date', 'code']).set_index('trade_date')\n",
"risk_return = pd.read_parquet('data/risk_return.parqut').sort_values('trade_date').set_index('trade_date')"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"risk_factors = risk_cov.columns[2:-1].tolist()\n",
"dates = risk_cov.index.unique().tolist()"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## 1. UQER v.s. TF Risk Model\n",
"--------------------"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"res = pd.DataFrame(columns=['UQER', 'TF', 'avg. vol', '# of Stk.'])\n",
"\n",
"window = '250b'\n",
"\n",
"for sample_date in dates[250:]:\n",
" \n",
" ## Uqer Risk Model\n",
" sample_risk_cov = risk_cov.loc[sample_date:sample_date, risk_factors]\n",
" sample_risk_exp = risk_exp.loc[sample_date:sample_date, ['code'] + risk_factors]\n",
" sample_specific_risk = specific_risk.loc[sample_date:sample_date, ['code', 'SRISK']]\n",
"\n",
" sample_codes = set(sample_risk_exp.code).intersection(sample_specific_risk.code)\n",
" sample_risk_exp = sample_risk_exp.loc[sample_risk_exp.code.isin(sample_codes)]\n",
" sample_specific_risk = sample_specific_risk.loc[sample_specific_risk.code.isin(sample_codes)]\n",
"\n",
" sample_risk_exp = sample_risk_exp[risk_factors].values\n",
" sample_risk_cov = sample_risk_cov.values\n",
" sample_specific_risk = sample_specific_risk['SRISK'].values\n",
" \n",
" explained_cov = sample_risk_exp @ sample_risk_cov @ sample_risk_exp.T / 10000.\n",
" sec_cov = explained_cov + np.diag(sample_specific_risk ** 2) / 10000\n",
" \n",
" explained_var = np.diag(explained_cov)\n",
" sec_var = np.diag(sec_cov)\n",
" explained_per = np.mean(explained_var / sec_var)\n",
" avg_vol = np.mean(np.sqrt(sec_var))\n",
" num_stks = len(sample_codes)\n",
" \n",
" ## TF Risk Model\n",
" start_date = advanceDateByCalendar('china.sse', sample_date, period= '-' + window)\n",
" sample_risk_return = risk_return[start_date:sample_date]\n",
" ret_values = sample_risk_return[risk_factors].T\n",
" tf_risk_cov = BarraCov(ret_values, 90, 20) * 10000 * 250\n",
" tf_explained_cov = sample_risk_exp @ tf_risk_cov @ sample_risk_exp.T / 10000.\n",
" tf_explained_var = np.diag(tf_explained_cov)\n",
" tf_explained_per = np.mean(tf_explained_var / sec_var)\n",
" \n",
" ## Output\n",
" res.loc[sample_date, 'UQER'] = explained_per\n",
" res.loc[sample_date, 'UQER (std.)'] = np.std(explained_var / sec_var)\n",
" res.loc[sample_date, 'UQER (# > 100%)'] = np.sum((explained_var / sec_var >= 1.))\n",
" res.loc[sample_date, 'TF'] = tf_explained_per\n",
" res.loc[sample_date, 'TF (std.)'] = np.std(tf_explained_var / sec_var)\n",
" res.loc[sample_date, 'TF (# > 100%)'] = np.sum((tf_explained_var / sec_var >= 1.))\n",
" res.loc[sample_date, 'avg. vol'] = avg_vol\n",
" res.loc[sample_date, '# of Stk.'] = num_stks\n",
" print(f\"{sample_date}: UQER: {explained_per:.2f}, {np.std(explained_var / sec_var):.2f}, {np.sum((explained_var / sec_var >= 1.)):0d} \\\n",
" TF: {tf_explained_per:.2f}, {np.std(tf_explained_var / sec_var):.2f}, {np.sum((tf_explained_var / sec_var >= 1.)):0d}\")"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"res.to_excel('uqer_vs_tf.xlsx')"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"res[['UQER', 'TF']].rolling(window=30).mean().plot(secondary_y='avg. vol', figsize=(16, 8))"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.7.3"
}
},
"nbformat": 4,
"nbformat_minor": 2
}
This diff is collapsed.
This diff is collapsed.
File added
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment