/// <summary> /// 获取前一天下跌的股票 /// </summary> public static List <String> GetLastDayCodes(int type) { List <String> ret = new List <String>(); foreach (String code in m_historyDatas.Keys) { List <SecurityData> sds = m_historyDatas[code]; SecurityData sd = sds[sds.Count - 1]; if (type == 0) { if (sd.m_close < sd.m_open) { ret.Add(code); } } else if (type == 1) { if (sd.m_close > sd.m_open) { ret.Add(code); } } } return(ret); }
/// <summary> /// 获取周线的历史数据 /// </summary> /// <param name="weekDatas">周线历史数据</param> /// <param name="dayDatas">日线历史数据</param> /// <returns>状态</returns> public static int GetHistoryWeekDatas(List <SecurityData> weekDatas, List <SecurityData> dayDatas) { int weekDatasSize = dayDatas.Count; if (weekDatasSize > 0) { SecurityData weekData = new SecurityData(); weekData.Copy(dayDatas[0]); int lDayOfWeek = 0, lDays = 0; for (int i = 0; i < weekDatasSize; i++) { SecurityData dayData = new SecurityData(); dayData.Copy(dayDatas[i]); int year = 0, month = 0, day = 0, hour = 0, minute = 0, second = 0, ms = 0, days = (int)dayData.m_date / (3600 * 24); CStrA.M130(dayData.m_date, ref year, ref month, ref day, ref hour, ref minute, ref second, ref ms); int dayOfWeek = DayOfWeek(year, month, day); bool isNextWeek = true; bool add = false; if (days - lDays <= 5) { if (days != lDays) { isNextWeek = dayOfWeek <= lDayOfWeek; } } if (isNextWeek || i == weekDatasSize - 1) { add = true; } if (!isNextWeek) { weekData.m_close = dayData.m_close; weekData.m_amount += dayData.m_amount; weekData.m_volume += dayData.m_volume; if (weekData.m_high < dayData.m_high) { weekData.m_high = dayData.m_high; } if (weekData.m_low > dayData.m_low) { weekData.m_low = dayData.m_low; } } if (add) { weekDatas.Add(weekData); weekData = dayData; } if (isNextWeek && i == weekDatasSize - 1) { weekData = dayData; weekDatas.Add(weekData); } lDayOfWeek = dayOfWeek; lDays = days; } } return(1); }
/// <summary> /// 获取通达信的历史数据 /// </summary> /// <param name="str">数据字符串</param> /// <param name="datas">历史数据</param> /// <returns>状态</returns> public static int GetHistoryDatasByTdxStr(String str, List <SecurityData> datas) { String[] strs = str.Split(new String[] { "\r\n" }, StringSplitOptions.RemoveEmptyEntries); int strLen = strs.Length; for (int i = 2; i < strLen - 1; i++) { String[] strs2 = strs[i].Split(','); int strs2Size = strs2.Length; if (strs2Size >= 7) { String[] dateStrs = strs2[0].Split('-'); int year = 0, month = 0, day = 0, hour = 0, minute = 0; if (dateStrs.Length == 3) { year = CStrA.ConvertStrToInt(dateStrs[0]); month = CStrA.ConvertStrToInt(dateStrs[1]); day = CStrA.ConvertStrToInt(dateStrs[2]); } int si = 1; if (strs2Size == 8) { si = 2; hour = CStrA.ConvertStrToInt(strs2[1].Substring(0, 2)); minute = CStrA.ConvertStrToInt(strs2[1].Substring(2, 2)); } double open = CStrA.ConvertStrToDouble(strs2[si]); double high = CStrA.ConvertStrToDouble(strs2[si + 1]); double low = CStrA.ConvertStrToDouble(strs2[si + 2]); double close = CStrA.ConvertStrToDouble(strs2[si + 3]); double volume = CStrA.ConvertStrToDouble(strs2[si + 4]); double amount = CStrA.ConvertStrToDouble(strs2[si + 5]); if (volume == 0) { continue; } if (year != 0 && month != 0 && day != 0) { SecurityData securityData = new SecurityData(); if (hour != 0 || minute != 0) { securityData.m_date = CStrA.M129(year, month, day, hour, minute, 0, 0) - 300; } else { securityData.m_date = CStrA.M129(year, month, day, 0, 0, 0, 0); } securityData.m_open = open; securityData.m_high = high; securityData.m_low = low; securityData.m_close = close; securityData.m_volume = volume; securityData.m_amount = amount; datas.Add(securityData); } } } return(1); }
/// <summary> /// 复制数据 /// </summary> /// <param name="data">数据</param> public void Copy(SecurityData data) { m_close = data.m_close; m_date = data.m_date; m_high = data.m_high; m_low = data.m_low; m_open = data.m_open; m_volume = data.m_volume; m_amount = data.m_amount; }
/// <summary> /// 获取月线的历史数据 /// </summary> /// <param name="weekDatas">月线历史数据</param> /// <param name="dayDatas">日线历史数据</param> /// <returns>状态</returns> public static int GetHistoryMonthDatas(List <SecurityData> monthDatas, List <SecurityData> dayDatas) { int monthDatasSize = dayDatas.Count; if (monthDatasSize > 0) { SecurityData monthData = new SecurityData(); monthData.Copy(dayDatas[0]); int lYear = 0, lMonth = 0, lDay = 0; for (int i = 0; i < monthDatasSize; i++) { SecurityData dayData = new SecurityData(); dayData.Copy(dayDatas[i]); int year = 0, month = 0, day = 0, hour = 0, minute = 0, second = 0, ms = 0; CStrA.M130(dayData.m_date, ref year, ref month, ref day, ref hour, ref minute, ref second, ref ms); bool isNextMonth = year * 12 + month > lYear * 12 + lMonth; bool add = false; if (i == monthDatasSize - 1 || (i > 0 && isNextMonth)) { add = true; } if (!isNextMonth) { monthData.m_close = dayData.m_close; monthData.m_amount += dayData.m_amount; monthData.m_volume += dayData.m_volume; if (monthData.m_high < dayData.m_high) { monthData.m_high = dayData.m_high; } if (monthData.m_low > dayData.m_low) { monthData.m_low = dayData.m_low; } } if (add) { monthDatas.Add(monthData); monthData = dayData; } if (isNextMonth && i == monthDatasSize - 1) { monthData = dayData; monthDatas.Add(monthData); } lYear = year; lMonth = month; lDay = day; } } return(1); }
/// <summary> /// 插入数据 /// </summary> /// <param name="chart">证券控件</param> /// <param name="dataSource">数据源</param> /// <param name="fields">字段</param> /// <param name="securityData">证券数据</param> /// <returns>索引</returns> public static int InsertData(ChartA chart, CTable dataSource, int[] fields, SecurityData securityData) { double close = securityData.m_close, high = securityData.m_high, low = securityData.m_low, open = securityData.m_open, avgPrice = securityData.m_avgPrice, volume = securityData.m_volume, amount = securityData.m_amount; if (volume > 0 || close > 0) { if (high == 0) { high = close; } if (low == 0) { low = close; } if (open == 0) { open = close; } if (avgPrice == 0) { avgPrice = double.NaN; } } else { close = double.NaN; high = double.NaN; low = double.NaN; open = double.NaN; volume = double.NaN; amount = double.NaN; avgPrice = double.NaN; } double date = securityData.m_date; dataSource.Set(date, fields[4], volume); int index = dataSource.GetRowIndex(date); dataSource.Set2(index, fields[0], close); dataSource.Set2(index, fields[1], high); dataSource.Set2(index, fields[2], low); dataSource.Set2(index, fields[3], open); dataSource.Set2(index, fields[5], amount); dataSource.Set2(index, fields[6], avgPrice); return(index); }
public static void BindHistoryVolAndAmountDatas(ChartAEx chart, CTable dataSource, int[] fields, List <SecurityData> historyDatas) { dataSource.Clear(); int size = (int)historyDatas.Count;; dataSource.SetRowsCapacity(size + 10); dataSource.SetRowsGrowStep(100); int columnsCount = dataSource.ColumnsCount; for (int i = 0; i < size; i++) { SecurityData securityData = historyDatas[i]; double[] ary = new double[columnsCount]; ary[0] = securityData.m_volume; ary[1] = securityData.m_amount; dataSource.AddRow((double)securityData.m_date, ary, columnsCount); } }
/// <summary> /// 获取分时数据 /// </summary> public static void GetMinuteDatas() { if (m_minuteDatas.Count > 0) { return; } String appPath = DataCenter.GetAppPath(); foreach (String code in m_codedMap.Keys) { String fileName = m_newFileDir + CStrA.ConvertDBCodeToFileName(code); if (!CFileA.IsFileExist(fileName)) { fileName = m_newFileDir + CStrA.ConvertDBCodeToSinaCode(code).ToUpper() + ".txt"; } if (CFileA.IsFileExist(fileName)) { String text = ""; CFileA.Read(fileName, ref text); List <SecurityData> datas = new List <SecurityData>(); StockService.GetHistoryDatasByMinuteStr(text, datas); if (datas.Count > 0) { int rindex = 0; int dataSize = datas.Count; while (rindex < dataSize) { SecurityData d = datas[rindex]; if (rindex == 0) { d.m_avgPrice = d.m_close; } else { SecurityData ld = datas[rindex - 1]; d.m_avgPrice = (ld.m_avgPrice * rindex + d.m_close) / (rindex + 1); } rindex++; } m_minuteDatas[code] = datas; } } } }
/// <summary> /// 计算指标 /// </summary> /// <param name="id">指标ID</param> /// <param name="code">代码</param> /// <returns>返回数据</returns> public static Dictionary <String, double> CalculateIndicatorExtern(int id, String code) { Dictionary <String, double> list = new Dictionary <String, double>(); if (m_indicators.ContainsKey(id) && SecurityService.m_historyDatas.ContainsKey(code) && SecurityService.m_latestDatas.ContainsKey(code)) { CIndicator indicator = m_indicators[id]; List <CIndicator> indicators = new List <CIndicator>(); indicators.Add(indicator); List <SecurityData> datas = new List <SecurityData>(); List <SecurityData> oldSecurityDatas = SecurityService.m_historyDatas[code]; int oldSecurityDatasSize = oldSecurityDatas.Count; for (int i = 0; i < oldSecurityDatasSize; i++) { datas.Add(oldSecurityDatas[i]); } SecurityLatestData latestData = SecurityService.m_latestDatas[code]; SecurityData newData = new SecurityData(); StockService.GetSecurityData(latestData, latestData.m_lastClose, 1440, 1, ref newData); datas.Add(newData); CTable dataSource = indicator.DataSource; int[] fields = new int[] { KeyFields.CLOSE_INDEX, KeyFields.HIGH_INDEX, KeyFields.LOW_INDEX, KeyFields.OPEN_INDEX, KeyFields.VOL_INDEX, KeyFields.AMOUNT_INDEX }; SecurityDataHelper.BindHistoryDatas(m_chart, dataSource, indicators, fields, datas); datas.Clear(); int rowsCount = dataSource.RowsCount; int variablesSize = indicator.MainVariables.Count; if (rowsCount > 0) { foreach (String name in indicator.MainVariables.Keys) { int field = indicator.MainVariables[name]; double value = dataSource.Get2(rowsCount - 1, field); list[name] = value; } } dataSource.Clear(); } return(list); }
public static void BindHistoryDatas(ChartAEx chart, CTable dataSource, List <CIndicator> indicators, int[] fields, List <SecurityData> historyDatas) { dataSource.Clear(); int sizeData = (int)historyDatas.Count; if (sizeData > 0) { dataSource.SetRowsCapacity(sizeData + 10); dataSource.SetRowsGrowStep(100); int columnsCount = dataSource.ColumnsCount; for (int i = 0; i < sizeData; i++) { SecurityData securityData = historyDatas[i]; if (dataSource == chart.DataSource) { if (securityData.m_close > 0) { InsertData(chart, dataSource, fields, securityData); } } else { double[] ary = new double[columnsCount]; ary[0] = securityData.m_close; ary[1] = securityData.m_high; ary[2] = securityData.m_low; ary[3] = securityData.m_open; ary[4] = securityData.m_volume; ary[5] = securityData.m_amount; ary[6] = securityData.m_avgPrice; dataSource.AddRow((double)securityData.m_date, ary, columnsCount); } } int indicatorsSize = (int)indicators.Count; for (int i = 0; i < indicatorsSize; i++) { indicators[i].OnCalculate(0); } } }
/// <summary> /// 获取比例 /// </summary> /// <param name="fallCodes"></param> /// <returns></returns> public static Dictionary <String, double> Step5(List <String> fallCodes) { int index = 0; int size = fallCodes.Count; Dictionary <String, double> ret = new Dictionary <String, double>(); while (index < size) { if (m_minuteDatas.ContainsKey(fallCodes[index])) { List <SecurityData> datas = m_minuteDatas[fallCodes[index]]; if (datas != null) { SecurityData m = datas[datas.Count - 1]; double av = (m.m_close - m.m_avgPrice) / m.m_close; ret[fallCodes[index]] = av; } } index++; } return(ret); }
/// <summary> /// 插入最新数据 /// </summary> /// <param name="chart">股票控件</param> /// <param name="dataSource">数据源</param> /// <param name="indicators">指标</param> /// <param name="fields">字段</param> /// <param name="historyDatas">最近的历史数据</param> /// <param name="latestData">实时数据</param> /// <returns>索引</returns> public static int InsertLatestData(ChartA chart, CTable dataSource, List <CIndicator> indicators, int[] fields, SecurityData latestData) { if (latestData.m_close > 0 && latestData.m_volume > 0) { int indicatorsSize = indicators.Count; int index = InsertData(chart, dataSource, fields, latestData); for (int i = 0; i < indicatorsSize; i++) { indicators[i].OnCalculate(index); } return(index); } else { return(-1); } }
/// <summary> /// 获取股票历史数据 /// </summary> /// <param name="latestData">最新数据</param> /// <param name="lastClose">上一期收盘价</param> /// <param name="cycle">周期</param> /// <param name="subscription">复权模式</param> /// <param name="securityData">历史数据</param> /// <returns>历史数据</returns> public static void GetSecurityData(SecurityLatestData latestData, double lastClose, int cycle, int subscription, ref SecurityData securityData) { if (cycle <= 60) { securityData.m_date = GetDivideDate(latestData.m_date, 60 * 60); } else { securityData.m_date = (long)latestData.m_date / (3600 * 24) * (3600 * 24); } //前复权计算 double factor = 1; if (lastClose > 0 && latestData.m_lastClose > 0 && subscription == 2) { factor = lastClose / latestData.m_lastClose; } securityData.m_close = latestData.m_close * factor; securityData.m_high = latestData.m_high * factor; securityData.m_low = latestData.m_low * factor; securityData.m_open = latestData.m_open * factor; securityData.m_volume = latestData.m_volume; securityData.m_amount = latestData.m_amount; }
/// <summary> /// 获取分时线的历史数据 /// </summary> /// <param name="str">数据字符串</param> /// <param name="datas">历史数据</param> /// <returns>状态</returns> public static int GetHistoryDatasByMinuteStr(String str, List <SecurityData> datas) { String[] strs = str.Split(new String[] { "\r\n" }, StringSplitOptions.RemoveEmptyEntries); int strLen = strs.Length; double lClose = 0, lHigh = 0, lLow = 0, lOpen = 0; double lVolume = 0, lAmount = 0, fVolume = 0, fAmount = 0, sum = 0; int lYear = 0, lMonth = 0, lDay = 0, lHour = 0, lMinute = 0; int startIndex = 0; for (int i = startIndex; i < strLen; i++) { String[] strs2 = strs[i].Split(','); if (strs2.Length == 4) { double date = CStrA.ConvertStrToDouble(strs2[0]); double close = CStrA.ConvertStrToDouble(strs2[1]); double volume = CStrA.ConvertStrToDouble(strs2[2]); double amount = CStrA.ConvertStrToDouble(strs2[3]); int year = 0, month = 0, day = 0, hour = 0, minute = 0, second = 0, ms = 0; CStrA.M130(date, ref year, ref month, ref day, ref hour, ref minute, ref second, ref ms); if (hour * 60 + minute >= 899) { hour = 14; minute = 59; } if (i == startIndex) { lClose = close; lHigh = close; lLow = close; lOpen = close; lVolume = volume; lAmount = amount; lYear = year; lMonth = month; lDay = day; lHour = hour; lMinute = minute; } bool inSameTime = false; if (hour == lHour && minute == lMinute) { inSameTime = true; if (close > lHigh) { lHigh = close; } if (close < lLow) { lLow = close; } } if (!inSameTime || i == strLen - 1) { SecurityData data = new SecurityData(); data.m_date = CStrA.M129(lYear, lMonth, lDay, lHour, lMinute, 0, 0); data.m_close = lClose; if (lHigh != 0) { data.m_high = lHigh; } else { data.m_high = lClose; } if (lLow != 0) { data.m_low = lLow; } else { data.m_low = lClose; } if (lOpen != 0) { data.m_open = lOpen; } else { data.m_open = lClose; } data.m_volume = lVolume - fVolume; data.m_amount = lAmount - fAmount; if (data.m_close != 0 && data.m_volume != 0) { sum += data.m_close; data.m_avgPrice = sum / (datas.Count + 1); datas.Add(data); } fVolume = lVolume; fAmount = lAmount; } if (!inSameTime) { lHigh = close; lLow = close; lOpen = close; lYear = year; lMonth = month; lDay = day; lHour = hour; lMinute = minute; } lClose = close; lVolume = volume; lAmount = amount; } } return(1); }
/// <summary> /// 数据落地线程工作 /// </summary> public static void StartWork3() { //复制数据 LoadHistoryDatas(); GetMinuteDatas(); //新旧数据合并 foreach (String oCode in m_historyDatas.Keys) { if (!m_latestDatas.ContainsKey(oCode) || !m_historyDatas.ContainsKey(oCode)) { continue; } SecurityLatestData securityLatestData = m_latestDatas[oCode]; List <SecurityData> oldSecurityDatas = m_historyDatas[oCode]; SecurityData oldSecurityData = oldSecurityDatas[oldSecurityDatas.Count - 1]; int myear = 0, mmonth = 0, mday = 0, mhour = 0, mmin = 0, msec = 0, mmsec = 0; CStrA.M130(oldSecurityData.m_date, ref myear, ref mmonth, ref mday, ref mhour, ref mmin, ref msec, ref mmsec); int year = 0, month = 0, day = 0, hour = 0, min = 0, sec = 0, msec2 = 0; CStrA.M130(securityLatestData.m_date, ref year, ref month, ref day, ref hour, ref min, ref sec, ref msec2); if (year >= myear && month >= mmonth && day >= mday) { SecurityData nSecurityData = new SecurityData(); nSecurityData.m_amount = securityLatestData.m_amount; nSecurityData.m_close = securityLatestData.m_close; nSecurityData.m_date = securityLatestData.m_date; nSecurityData.m_high = securityLatestData.m_high; nSecurityData.m_low = securityLatestData.m_low; nSecurityData.m_open = securityLatestData.m_open; nSecurityData.m_volume = securityLatestData.m_volume; if (day == mday) { m_historyDatas[oCode].RemoveAt(m_historyDatas[oCode].Count - 1); } m_historyDatas[oCode].Add(nSecurityData); } } String outputFileTemplate = DataCenter.GetAppPath() + "\\day\\{0}.txt"; String fileInfo = "{0} {1} 日线 前复权\r\n"; String title = " 日期 开盘 最高 最低 收盘 成交量 成交额\r\n"; String lineTemp = "{0},{1},{2},{3},{4},{5},{6}\r\n"; String timeFormatStr = "yyyy-MM-dd"; //写入文件 foreach (String code in m_historyDatas.Keys) { List <SecurityData> temp3 = m_historyDatas[code]; StringBuilder strbuff = new StringBuilder(); strbuff.Append(String.Format(fileInfo, m_codedMap[code].m_code, m_codedMap[code].m_name)); strbuff.Append(title); foreach (SecurityData sdt in temp3) { strbuff.Append(String.Format(lineTemp, // CStr.ConvertNumToDate(sdt.m_date).ToString(timeFormatStr), // sdt.m_open, // sdt.m_high, // sdt.m_low, // sdt.m_close, // sdt.m_volume, // sdt.m_amount)); } strbuff.Append("数据来源:通达信\r\n"); CFileA.Write(String.Format(outputFileTemplate, code), strbuff.ToString()); } }