{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "* 请在环境变量中设置`DB_URI`指向数据库"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "%matplotlib inline\n",
    "import os\n",
    "import datetime as dt\n",
    "import numpy as np\n",
    "import pandas as pd\n",
    "from PyFin.api import *\n",
    "from alphamind.api import *\n",
    "from matplotlib import pyplot as plt\n",
    "\n",
    "plt.style.use('ggplot')\n",
    "dt.datetime.now()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "start_date = '2017-04-10'\n",
    "end_date = '2018-04-09'\n",
    "\n",
    "freq = '5b'\n",
    "horizon = map_freq(freq)\n",
    "neutralized_risk = risk_styles + industry_styles\n",
    "universe = Universe('zz500')\n",
    "data_source = os.environ['DB_URI']\n",
    "offset = 1\n",
    "method = 'ls'\n",
    "industry_name = 'sw'\n",
    "industry_level = 1\n",
    "\n",
    "risk_model = 'short'\n",
    "executor = NaiveExecutor()\n",
    "ref_dates = makeSchedule(start_date, end_date, freq, 'china.sse')\n",
    "engine = SqlEngine(data_source)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "alpha_factors = {\n",
    "    'f01': LAST('EPS'),\n",
    "    'f02': LAST('ROE')\n",
    "    }\n",
    "\n",
    "weights = dict(f01=1.0,\n",
    "               f02=1.0,\n",
    "              )\n",
    "\n",
    "alpha_model = ConstLinearModel(features=alpha_factors, weights=weights)\n",
    "\n",
    "def predict_worker(params):\n",
    "    data_meta = DataMeta(freq=freq,\n",
    "                         universe=universe,\n",
    "                         batch=1,\n",
    "                         neutralized_risk=neutralized_risk,\n",
    "                         risk_model='short',\n",
    "                         pre_process=[winsorize_normal, standardize],\n",
    "                         post_process=[standardize],\n",
    "                         warm_start=0,\n",
    "                         data_source=data_source)\n",
    "    ref_date, model = params\n",
    "    er = predict_by_model(ref_date, model, data_meta)\n",
    "    return er"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "%%time\n",
    "predicts = [predict_worker((d.strftime('%Y-%m-%d'), alpha_model)) for d in ref_dates]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "industry_names = industry_list(industry_name, industry_level)\n",
    "industry_total = engine.fetch_industry_matrix_range(universe, dates=ref_dates, category=industry_name, level=industry_level)\n",
    "\n",
    "previous_pos = pd.DataFrame()\n",
    "rets = []\n",
    "turn_overs = []\n",
    "leverags = []\n",
    "\n",
    "for i, ref_date in enumerate(ref_dates):\n",
    "    ref_date = ref_date.strftime('%Y-%m-%d')\n",
    "    industry_matrix = industry_total[industry_total.trade_date == ref_date]\n",
    "    \n",
    "    res = industry_matrix.dropna()\n",
    "    codes = res.code.values.tolist()\n",
    "        \n",
    "    er = predicts[i].loc[codes].values\n",
    "    \n",
    "    alpha_logger.info('{0} full re-balance: {1}'.format(ref_date, len(er)))\n",
    "    target_pos, _ = er_portfolio_analysis(er,\n",
    "                                          industry_matrix.industry_name.values,\n",
    "                                          None,\n",
    "                                          None,\n",
    "                                          False,\n",
    "                                          None,\n",
    "                                          method=method)\n",
    "        \n",
    "    target_pos['code'] = codes\n",
    "    turn_over, executed_pos = executor.execute(target_pos=target_pos)\n",
    "\n",
    "    executed_codes = executed_pos.code.tolist()\n",
    "    dx_returns = engine.fetch_dx_return(ref_date, executed_codes, horizon=horizon, offset=offset)\n",
    "    result = pd.merge(executed_pos, dx_returns, on=['code'])\n",
    "\n",
    "    leverage = result.weight.abs().sum()\n",
    "\n",
    "    ret = result.weight.values @ (np.exp(result.dx.values) - 1.)\n",
    "    rets.append(np.log(1. + ret))\n",
    "    executor.set_current(executed_pos)\n",
    "    turn_overs.append(turn_over)\n",
    "    leverags.append(leverage)\n",
    "\n",
    "    previous_pos = executed_pos\n",
    "    alpha_logger.info('{0} is finished'.format(ref_date))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "ret_df = pd.DataFrame({'returns': rets, 'turn_over': turn_overs, 'leverage': leverags}, index=ref_dates)\n",
    "ret_df.loc[advanceDateByCalendar('china.sse', ref_dates[-1], freq)] = 0.\n",
    "ret_df = ret_df.shift(1)\n",
    "ret_df.iloc[0] = 0.\n",
    "ret_df['tc_cost'] = ret_df.turn_over * 0.002\n",
    "\n",
    "ret_df[['returns', 'tc_cost']].cumsum().plot(figsize=(12, 6),\n",
    "                                             title='Fixed freq rebalanced: {0}'.format(freq),\n",
    "                                             secondary_y='tc_cost')"
   ]
  },
  {
   "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.6.5"
  },
  "varInspector": {
   "cols": {
    "lenName": 16,
    "lenType": 16,
    "lenVar": 40
   },
   "kernels_config": {
    "python": {
     "delete_cmd_postfix": "",
     "delete_cmd_prefix": "del ",
     "library": "var_list.py",
     "varRefreshCmd": "print(var_dic_list())"
    },
    "r": {
     "delete_cmd_postfix": ") ",
     "delete_cmd_prefix": "rm(",
     "library": "var_list.r",
     "varRefreshCmd": "cat(var_dic_list()) "
    }
   },
   "types_to_exclude": [
    "module",
    "function",
    "builtin_function_or_method",
    "instance",
    "_Feature"
   ],
   "window_display": false
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
