def get_call_put_impliedVols_tbcurve( evalDate, daycounter, calendar, maxVol=1.0, step=0.0001, precision=0.05, show=True): call_volatilities_0 = {} call_volatilities_1 = {} call_volatilities_2 = {} call_volatilities_3 = {} put_volatilites_0 = {} put_volatilites_1 = {} put_volatilites_2 = {} put_volatilites_3 = {} e_date0, e_date1, e_date2, e_date3 = 0, 0, 0, 0 try: curve = get_curve_treasury_bond(evalDate, daycounter) vols, spot, mktData, mktFlds, optionData, optionFlds, optionids = get_wind_data(evalDate) ql.Settings.instance().evaluationDate = evalDate yield_ts = ql.YieldTermStructureHandle(curve) dividend_ts = ql.YieldTermStructureHandle(ql.FlatForward(evalDate, 0.0, daycounter)) month_indexs = get_contract_months(evalDate) for idx, optionid in enumerate(optionids): optionDataIdx = optionData[optionFlds.index('wind_code')].index(optionid) mdate = pd.to_datetime(optionData[optionFlds.index('exercise_date')][optionDataIdx]) maturitydt = ql.Date(mdate.day, mdate.month, mdate.year) mktindex = mktData[mktFlds.index('option_code')].index(optionid) strike = optionData[optionFlds.index('exercise_price')][optionDataIdx] close = mktData[mktFlds.index('close')][mktindex] ttm = daycounter.yearFraction(evalDate, maturitydt) rf = curve.zeroRate(maturitydt, daycounter, ql.Continuous).rate() nbr_month = maturitydt.month() if nbr_month == month_indexs[0]: e_date0 = maturitydt Ft = spot * math.exp(rf * ttm) moneyness = math.log(strike / Ft, math.e) if optionData[optionFlds.index('call_or_put')][optionDataIdx] == '认购': optiontype = ql.Option.Call implied_vol, error = calculate_vol_BS(maturitydt, optiontype, strike, spot, dividend_ts, yield_ts, close, evalDate, calendar, daycounter, precision, maxVol, step) call_volatilities_0.update({moneyness: [implied_vol, strike, close]}) else: optiontype = ql.Option.Put implied_vol, error = calculate_vol_BS(maturitydt, optiontype, strike, spot, dividend_ts, yield_ts, close, evalDate, calendar, daycounter, precision, maxVol, step) put_volatilites_0.update({moneyness: [implied_vol, strike, close]}) elif nbr_month == month_indexs[1]: e_date1 = maturitydt Ft = spot * math.exp(rf * ttm) moneyness = math.log(strike / Ft, math.e) if optionData[optionFlds.index('call_or_put')][optionDataIdx] == '认购': optiontype = ql.Option.Call implied_vol, error = calculate_vol_BS(maturitydt, optiontype, strike, spot, dividend_ts, yield_ts, close, evalDate, calendar, daycounter, precision, maxVol, step) call_volatilities_1.update({moneyness: [implied_vol, strike, close]}) else: optiontype = ql.Option.Put implied_vol, error = calculate_vol_BS(maturitydt, optiontype, strike, spot, dividend_ts, yield_ts, close, evalDate, calendar, daycounter, precision, maxVol, step) put_volatilites_1.update({moneyness: [implied_vol, strike, close]}) elif nbr_month == month_indexs[2]: e_date2 = maturitydt Ft = spot * math.exp(rf * ttm) moneyness = math.log(strike / Ft, math.e) if optionData[optionFlds.index('call_or_put')][optionDataIdx] == '认购': optiontype = ql.Option.Call implied_vol, error = calculate_vol_BS(maturitydt, optiontype, strike, spot, dividend_ts, yield_ts, close, evalDate, calendar, daycounter, precision, maxVol, step) call_volatilities_2.update({moneyness: [implied_vol, strike, close]}) else: optiontype = ql.Option.Put implied_vol, error = calculate_vol_BS(maturitydt, optiontype, strike, spot, dividend_ts, yield_ts, close, evalDate, calendar, daycounter, precision, maxVol, step) put_volatilites_2.update({moneyness: [implied_vol, strike, close]}) else: e_date3 = maturitydt Ft = spot * math.exp(rf * ttm) moneyness = math.log(strike / Ft, math.e) if optionData[optionFlds.index('call_or_put')][optionDataIdx] == '认购': optiontype = ql.Option.Call implied_vol, error = calculate_vol_BS(maturitydt, optiontype, strike, spot, dividend_ts, yield_ts, close, evalDate, calendar, daycounter, precision, maxVol, step) call_volatilities_3.update({moneyness: [implied_vol, strike, close]}) else: optiontype = ql.Option.Put implied_vol, error = calculate_vol_BS(maturitydt, optiontype, strike, spot, dividend_ts, yield_ts, close, evalDate, calendar, daycounter, precision, maxVol, step) put_volatilites_3.update({moneyness: [implied_vol, strike, close]}) expiration_dates = [e_date0, e_date1, e_date2, e_date3] cal_vols = [call_volatilities_0, call_volatilities_1, call_volatilities_2, call_volatilities_3] put_vols = [put_volatilites_0, put_volatilites_1, put_volatilites_2, put_volatilites_3] except Exception as e: print('Error -- get_call_put_impliedVols failed') print(e) return return cal_vols, put_vols, expiration_dates, spot, curve
ql.Settings.instance().evaluationDate = evalDate try: #vols, spot, mktData, mktFlds, optionData, optionFlds, optionids = wind_data.get_wind_data(evalDate) cal_vols, put_vols, expiration_dates, spot, rf_months = svi_data.get_call_put_impliedVols_moneyness_PCPrate_pcvt( evalDate, daycounter, calendar, maxVol=1.0, step=0.0001, precision=0.001, show=False) data_months = svi_util.orgnize_data_for_optimization( evalDate, daycounter, cal_vols, put_vols, expiration_dates, spot) #print(data_months) except: continue key_date = datetime.date(evalDate.year(), evalDate.month(), evalDate.dayOfMonth()) maturity_dates = to_dt_dates(expiration_dates) svi_dataset = cal_vols, put_vols, maturity_dates, spot, rf_months daily_svi_dataset.update({key_date:svi_dataset}) dividend_ts = ql.YieldTermStructureHandle(ql.FlatForward(evalDate, 0.0, daycounter)) month_indexs = wind_data.get_contract_months(evalDate) params_months = [] for i in range(4): nbr_month = month_indexs[i] data = data_months.get(i) logMoneynesses = data[0] totalvariance = data[1] expiration_date = data[2] ttm = daycounter.yearFraction(evalDate, expiration_date) params = svi_util.get_svi_optimal_params(data, ttm, 30) params_months.append(params) daily_params.update({key_date:params_months}) dates.append(key_date) print('Finished : ',evalDate) print(params_months[0])
a_star = np.divide(_a_star, ttm) b_star = np.divide(_c_star, (sigma_star * ttm)) rho_star = np.divide(_d_star, _c_star) final_parames = [a_star, b_star, rho_star, m_star, sigma_star] return final_parames # Evaluation Settings np.random.seed() #w.start() calendar = ql.China() daycounter = ql.ActualActual() evalDate = ql.Date(18, 7, 2017) evalDate = calendar.advance(evalDate, ql.Period(1, ql.Days)) month_indexs = basic_data.get_contract_months(evalDate) ql.Settings.instance().evaluationDate = evalDate curve = basic_data.get_curve_treasury_bond(evalDate, daycounter) cal_vols, put_vols, expiration_dates, spot, risk_free_rates = svi_data.get_call_put_impliedVols_moneyness_PCPrate_pcvt( evalDate, daycounter, calendar, maxVol=1.0, step=0.0001, precision=0.001, show=False) data_months = svi_util.orgnize_data_for_optimization(evalDate, daycounter, cal_vols, put_vols, expiration_dates, spot) print(evalDate) # Calibrate SVI total variance curve