public void ComputeVol(int date, int[] time) { if (date < 20150416) { IHList = null;//2015年4月16之前IH不存在。 } if (date < 20150209) { optionList = null;//2015年2月9日之前50ETF期权不存在。 } OptionInformation myOption = new OptionInformation(date); optionList = myOption.GetOptionCodeByDate(date); optionListInt = myOption.GetOptionNameByDate(date); GetDataDaily myData = new GetDataDaily(date, IHList, optionList); foreach (var time0 in time) { this.time = time0; int index = TradeDays.TimeToIndex(time0); ImpvCurveOfCallMid = new SortedDictionary <double, SortedDictionary <double, double> >(); ImpvCurveOfPutMid = new SortedDictionary <double, SortedDictionary <double, double> >(); ComputeVolDaily(myData, index); string CsvName = "VolatilitySurfaceCallMid" + date.ToString() + time0.ToString() + ".csv"; SaveVolToCsv(CsvName, "call", "mid", ImpvCurveOfCallMid); CsvName = "VolatilitySurfacePutMid" + date.ToString() + time0.ToString() + ".csv"; SaveVolToCsv(CsvName, "put", "mid", ImpvCurveOfPutMid); } }
/// <summary> /// 将datatable转化为数组格式 /// </summary> /// <param name="str">交易代码</param> /// <param name="dt">数据</param> /// <returns>数组形式数据</returns> public levelOne[] DataTable2Array(string str, DataTable dt) { levelOne[] dtArr = new levelOne[28802]; for (int i = 0; i < dt.Rows.Count; i++) { levelOne data0 = new levelOne(); data0.code = str; int time = Convert.ToInt32(dt.Rows[i]["ttime"]); int index = TradeDays.TimeToIndex(time); if (index < 0 || index > 28801) { continue; } data0.time = time; data0.last = Convert.ToDouble(dt.Rows[i]["cp"]); data0.ask = Convert.ToDouble(dt.Rows[i]["S1"]); data0.askv = Convert.ToDouble(dt.Rows[i]["SV1"]); data0.bid = Convert.ToDouble(dt.Rows[i]["B1"]); data0.bidv = Convert.ToDouble(dt.Rows[i]["BV1"]); dtArr[index] = data0; } for (int i = 1; i < 28802; i++) { if (dtArr[i].last == 0) { dtArr[i] = new levelOne(dtArr[i - 1].code, dtArr[i - 1].time, dtArr[i - 1].last, dtArr[i - 1].ask, dtArr[i - 1].askv, dtArr[i - 1].bid, dtArr[i - 1].bidv); } } return(dtArr); }
/// <summary> /// 计算隐含波动率 /// </summary> /// <param name="myData">数据</param> /// <param name="index">时间下标</param> public void ComputeVolDaily(GetDataDaily myData, int index) { levelOne etfData = myData.dataDaily["510050.SH"][index]; foreach (int code in optionListInt) { string codeStr = code.ToString() + ".SH"; optionFormat option = OptionInformation.myOptionList[code]; levelOne optionData = myData.dataDaily[codeStr][index]; double duration = TradeDays.GetTimeSpan(date, option.endDate); Impv vol = new Impv(option, optionData, etfData, duration); double sigma = vol.computeVol(); GetCurve(option.strike, option.optionType, duration, sigma); } }
/// <summary> /// 按日期遍历,添加期权信息。写入静态哈希表myOptionList。 /// </summary> /// <param name="startDate">开始日期</param> /// <param name="endDate">结束日期</param> private void GetOptionInformationList(int startDate, int endDate) { //定义交易日期的类。 TradeDays myTradeDays = new TradeDays(startDate, endDate); //从数据库表中获取信息,如果已经是完整信息就不需要连接万德数据库。 if (GetOptionListFromTable(startDate, endDate) == true) { return; } //按日期遍历,添加期权信息。 WindAPI w = new WindAPI(); w.start(); foreach (int today in myTradeDays.myTradeDays) { if (TradeDays.IsOptionExerciseDate(today) || today == myTradeDays.myTradeDays[myTradeDays.myTradeDays.Count - 1]) { WindData optionToday = w.wset("OptionChain", "date=" + today.ToString() + ";us_code=" + Configuration.underlyingAsset + ";option_var=;month=全部;call_put=全部"); object[] optionList = optionToday.data as object[]; int num = optionList.Length / 13; for (int i = 0; i < num; i++) { optionFormat option = new optionFormat(); string codeString = (string)optionList[i * 13 + 4 - 1]; option.optionCode = Convert.ToInt32(codeString.Substring(0, 8)); option.market = codeString.Substring(9, 2); option.optionName = (string)optionList[i * 13 + 5 - 1]; option.executeType = (string)optionList[i * 13 + 6 - 1]; option.strike = (double)optionList[i * 13 + 7 - 1]; option.optionType = (string)optionList[i * 13 + 9 - 1]; option.startDate = TradeDays.DateTimeToInt((DateTime)optionList[i * 13 + 10 - 1]); option.endDate = TradeDays.DateTimeToInt((DateTime)optionList[i * 13 + 11 - 1]); if (myOptionList.ContainsKey(option.optionCode) == false) { myOptionList.Add(option.optionCode, option); } } } } w.stop(); }