/*
*********************************************************
* PROCESS THE DATA AND SHARE THEM WITH OTHER SOFTWARE.
*********************************************************
*/
void CDataProcess::DataProcess(){
	if(COMM_SHAREDMEM == g_CommunicationSel){
		//USING SHARED MEMERY.
		BOOL bTimeout = gEventRecv.Lock(INFINITE);
		UploadData();
		gEventRecv.Unlock();
		gEventSend.SetEvent();//SEND DATA.
	}
	else if(COMM_NETWORK == g_CommunicationSel){
		//USING TCP
		//UploadData();
		//gEventSend.SetEvent();

		//TELL THE SERVER TO SEND THE DATA
		SetEvent(h_eSingleSpectraSending);
	}
	else if(COMM_NONE == g_CommunicationSel){
		//SetEvent(h_eSingleSpectraSending);
		global.series_fifo.append(rq);
	    
	}
}
Beispiel #2
0
UINT IfEntry(LPVOID pParam){
	IfInData * data = (IfInData*)pParam;
	CThostFtdcInputOrderField req;
	memset(&req, 0, sizeof(req));
	///经纪公司代码
	strcpy(req.BrokerID, BROKER_ID);
	///投资者代码
	strcpy(req.InvestorID, INVESTOR_ID);
	///合约代码
	strcpy(req.InstrumentID, INSTRUMENT_ID);
	///报单引用
	//strcpy(req.OrderRef, ORDER_REF);
	sprintf(req.OrderRef,"%d",data->orf);
	///用户代码
	//	TThostFtdcUserIDType	UserID;
	///报单价格条件: 限价
	req.OrderPriceType = THOST_FTDC_OPT_LimitPrice;
	///买卖方向: 
	if(data->isbuy){
		req.Direction = THOST_FTDC_D_Buy;
	}
	else{
		req.Direction = THOST_FTDC_D_Sell;
	}
	///组合开平标志: 开仓
	if(!data->isflat){
		req.CombOffsetFlag[0] = THOST_FTDC_OF_Open;
	}
	else{
		req.CombOffsetFlag[0] = THOST_FTDC_OF_Close;
	}
	///组合投机套保标志
	req.CombHedgeFlag[0] = THOST_FTDC_HF_Speculation;
	///价格
	::EnterCriticalSection(&g_IfPrice);
	if(!data->isbuy){
		req.LimitPrice = ifBid1 - 150.0;
#ifdef _debug
		req.LimitPrice = ifAsk1 + 3;
#endif
	}
	else{
		req.LimitPrice = ifAsk1 + 150.0;
#ifdef _debug
		req.LimitPrice = ifBid1 - 3;
#endif
	}
	::LeaveCriticalSection(&g_IfPrice);
	///数量: 1
	req.VolumeTotalOriginal = data->numif;
	///有效期类型: 当日有效
	req.TimeCondition = THOST_FTDC_TC_GFD;
	///GTD日期
	//	TThostFtdcDateType	GTDDate;
	///成交量类型: 任何数量
	req.VolumeCondition = THOST_FTDC_VC_AV;
	///最小成交量: 1
	req.MinVolume = 1;
	///触发条件: 立即
	req.ContingentCondition = THOST_FTDC_CC_Immediately;
	///止损价
	//	TThostFtdcPriceType	StopPrice;
	///强平原因: 非强平
	req.ForceCloseReason = THOST_FTDC_FCC_NotForceClose;
	///自动挂起标志: 否
	req.IsAutoSuspend = 0;
	///业务单元
	//	TThostFtdcBusinessUnitType	BusinessUnit;
	///请求编号
	//	TThostFtdcRequestIDType	RequestID;
	///用户强评标志: 否
	req.UserForceClose = 0;

	std::vector<CThostFtdcOrderField> orderRes;
	std::map<CString,std::vector<CThostFtdcOrderField>>::iterator iOrderRtn;
	std::map<CString,std::vector<CThostFtdcTradeField>>::iterator iTradeRtn;
	std::vector<CThostFtdcOrderField>::iterator iOrderRtnVec;
	std::vector<CThostFtdcTradeField>::iterator iTradeRtnVec;
	CThostFtdcInputOrderActionField reqNew = {'0','0',0,'0',0,0,0,'0','0','0','0',0,0,'0','0'};//命令动作新的修改
	CThostFtdcOrderField orderOld;
	CString thisSysId;//系统编号,作为已成交合约的识别码
	CString thisRef(req.OrderRef);
	double valueTraded = 0;//成交总价值
	bool isBreakIn = false;//是否因为cancel命令提前终止消息循环
	int volumeTraded = 0;
	int endVolumeThisTrade = 0;
	SYSTEMTIME sys;
	while(true){
		GetLocalTime(&sys);
		if(sys.wHour == 9 && sys.wMinute <= 14){
			//9:15前不下单,等待
			continue;
		}
		else{
			break;
		}
	}
	::EnterCriticalSection(&REQUEST_ID_IF);
	int iResult = pUserApi->ReqOrderInsert(&req, ++iRequestID);
	endVolumeThisTrade = req.VolumeTotalOriginal;
	::LeaveCriticalSection(&REQUEST_ID_IF);
	int lastpos = -1;//命令返回消息队列已经处理的位置
	while(true){ 
		//消息返回处理
		int size = 0;
		SwitchToThread();
		::EnterCriticalSection(&ifDealRtn);
		iOrderRtn = ifOrderRtn.find(thisRef);
		if(iOrderRtn != ifOrderRtn.end() && iOrderRtn->second.size() != 0){//证明里边已经有了消息
			//if(iOrderRtn->second.size() != 0){
			size = iOrderRtn->second.size();
			for(int k = 0/*lastpos + 1*/;k < size;k++){
				iOrderRtnVec = iOrderRtn->second.begin() + k;
				orderOld = *iOrderRtnVec;//获取返回的报单命令,状态会不停变化,取到队列末尾,取最新的命令
				thisSysId = iOrderRtnVec->OrderSysID;//获取报单编号
				TRACE("报单引用=%s,报单编号=%s\r\n",iOrderRtnVec->OrderRef,thisSysId);
				/*
				//不管什么原因,均表示已经traded
				if(iOrderRtnVec->VolumeTraded == iOrderRtnVec->VolumeTotalOriginal){
				TRACE("%s\r\n","已经成交,但是从OrderRtn返回");
				::EnterCriticalSection(&avgPriceOfIf);
				valueTraded = valueTraded + iOrderRtnVec->VolumeTraded * iOrderRtnVec->LimitPrice;
				avgpIf avg(data->numif,valueTraded / data->numif);
				avgPriceIf.push_back(avg);
				::LeaveCriticalSection(&avgPriceOfIf);
				//删除键值
				ifOrderRtn.erase(iOrderRtn);
				TRACE("准备脱离ifDealRtn临界区\r\n");
				::LeaveCriticalSection(&ifDealRtn);
				delete (IfInData*)pParam;
				return 0;
				}
				*/
				//如果取消,重新下单
				if(iOrderRtnVec->OrderStatus == THOST_FTDC_OST_Canceled){
					endVolumeThisTrade = endVolumeThisTrade - (iOrderRtnVec->VolumeTotalOriginal - iOrderRtnVec->VolumeTraded);					
					//删除键值
					//ifOrderRtn.erase(iOrderRtn);
					/*
					isBreakIn = true;
					break;//终止内循环
					*/
				}
			}
			/*
			if(isBreakIn){
			isBreakIn = false;
			lastpos = -1;//重新设置
			::LeaveCriticalSection(&ifDealRtn);
			continue;
			}
			*/
			//lastpos = size - 1;
			//iOrderRtn->second.clear();//清空就可以从0头开始检索
			::LeaveCriticalSection(&ifDealRtn);
			//}
		}
		else{
			//还没生成消息队列,表示指令还未生效,返回继续搜索队列
			::LeaveCriticalSection(&ifDealRtn);
			TRACE("%s\r\n","还没生成消息队列,返回");
			continue;
		}
		//成交返回处理
		::EnterCriticalSection(&ifDealRtn);
		if(endVolumeThisTrade == 0){
			return 0;
		}
		else{
			iTradeRtn = ifTradeRtn.find(thisSysId);
			//证明已经有成交信息返回
			if(iTradeRtn != ifTradeRtn.end()){
				for(iTradeRtnVec = iTradeRtn->second.begin();iTradeRtnVec != iTradeRtn->second.end();iTradeRtnVec++){
					TRACE("%s报单编号是%s\r\n","成交,从TradeRtn返回,",iTradeRtn->second.begin()->OrderSysID);
					::EnterCriticalSection(&avgPriceOfIf);
					valueTraded = valueTraded + iTradeRtnVec->Price * iTradeRtnVec->Volume;
					volumeTraded = volumeTraded + iTradeRtnVec->Volume;
					if(volumeTraded == data->numif){//全部成交
						avgpIf avg(volumeTraded,valueTraded / volumeTraded);
						avgPriceIf.push_back(avg);
						::LeaveCriticalSection(&avgPriceOfIf);
						//删除键值
						ifTradeRtn.erase(iTradeRtn);
						ifOrderRtn.erase(iOrderRtn);
						::LeaveCriticalSection(&ifDealRtn);
						return 0;
					}
					::LeaveCriticalSection(&avgPriceOfIf);
				}
				iTradeRtn->second.clear();//将成交数组清空
			}
		}
		::LeaveCriticalSection(&ifDealRtn);
		if(volumeTraded == endVolumeThisTrade && endVolumeThisTrade < data->numif){//本次成交结束,但是还没有全部成交,需要重新下单
			TRACE("%s\r\n","重新下单");
			::EnterCriticalSection(&g_IfPrice);
			if(req.Direction == THOST_FTDC_D_Buy){//BUY
				req.LimitPrice = ifBid1;
#ifdef _debug
				req.LimitPrice = ifBid1;
#endif
			}
			else{//SELL
				req.LimitPrice = ifAsk1;
#ifdef _debug
				req.LimitPrice = ifAsk1;
#endif
			}
			::LeaveCriticalSection(&g_IfPrice);
			req.VolumeTotalOriginal = data->numif - endVolumeThisTrade;
			endVolumeThisTrade = data->numif;//重新设置
			::EnterCriticalSection(&ODREF);
			iNextOrderRef++;
			TThostFtdcOrderRefType orderRefNew;
			sprintf(orderRefNew,"%d", iNextOrderRef);
			::LeaveCriticalSection(&ODREF);
			strcpy(req.OrderRef,orderRefNew);
			thisRef = CString(orderRefNew);
			::EnterCriticalSection(&REQUEST_ID_IF);
			int iResult = pUserApi->ReqOrderInsert(&req, ++iRequestID);
			::LeaveCriticalSection(&REQUEST_ID_IF);
		}
		//如果价格发生不利变化,取消订单 
		UpdateTrade.Lock(INFINITE);//等待同步事件击发
		::EnterCriticalSection(&g_IfPrice);
		if((req.Direction == THOST_FTDC_D_Buy && req.LimitPrice < ifBid1) ||//买
			(req.Direction == THOST_FTDC_D_Sell && req.LimitPrice > ifAsk1)){//卖
				if (IsTradingOrder(&orderOld)){
					TRACE("%s\r\n","改单动作,删除");
					ReqOrderAction(&orderOld,reqNew);
				}
		}
		::LeaveCriticalSection(&g_IfPrice);
	}
	delete (IfInData*)pParam;
	return iResult;
}
Beispiel #3
0
int flatOrOpen(int num,bool isbuy,bool isflat){
	if(num <= 0){
		return -1;
	}
	::EnterCriticalSection(&avgPriceOfIf);
	avgPriceIf.clear();//清空统计平均价格的数组
	::LeaveCriticalSection(&avgPriceOfIf);
	int numAvail = 0;//容许开仓数量
	if(!isflat){//表示开仓
		/*
		ReqAccount.ResetEvent();//事件同步,设置为未发信状态
		ReqQryIFTradingAccount();//查询if帐户可用资金
		ReqAccount.Lock(INFINITE);//等待
		if(rtnAvailIfID == rqIfID){
		//留有10和100人民币的余地
		marginIf = ifAsk1 * 300.0 * 0.12;//12%的保证金率
		if(multiply != 0){
		numAvail = min((int)((availA50  - 10.0) / (marginA50 * multiply)),(int)((availIf - 100.0) / marginIf));
		}
		else{
		numAvail = num;
		}
		}
		if(numAvail <= 0){
		return -1;
		}
		num = min(num,numAvail);
		*/
	}
	if(isflat){
		if(isbuy){
			TRACE("买平%d手\r\n",num);
		}
		else{
			TRACE("卖平%d手\r\n",num);
		}
	}
	else{
		if(isbuy){
			TRACE("买开%d手\r\n",num);
		}
		else{
			TRACE("卖开%d手\r\n",num);
		}
	}
	int numofA50 = num * multiply;
	int numofIf = num;
	std::vector<HANDLE> handleThread;//存放线程句柄的数组
	IfInData *data;
	if(isbuy && isflat){
		data = new IfInData(1,false,true,0); 
	}
	else if(isbuy && !isflat)
	{
		data = new IfInData(1,false,false,0);
	}
	else if(!isbuy && isflat){
		data = new IfInData(1,true,true,0);
	}
	else{
		data = new IfInData(1,true,false,0);
	}
	if(numofA50 != 0){
#define PUT(prop,value) orderA50.get()->##prop## = (##value##);
#define GET(prop) orderA50.get()->##prop
		std::auto_ptr<Order> orderA50(new Order());
		double valueTradeA50 = 0;
		::EnterCriticalSection(&g_A50Price);
		if(isbuy){
			PUT(action,"BUY");
			PUT(totalQuantity,numofA50);
#ifdef _case1
			PUT(lmtPrice,a50Ask1 + 100.0);
#else
			PUT(lmtPrice,a50Bid1);
#endif
			PUT(orderType,"LMT");
		}
		else{
			PUT(action,"SELL");
			PUT(totalQuantity,numofA50);
#ifdef _case1
			PUT(lmtPrice,a50Bid1 - 100.0);
#else
			PUT(lmtPrice,a50Ask1);
#endif
			PUT(orderType,"LMT");
		}
		::LeaveCriticalSection(&g_A50Price);
		bool isA50Validate = false;
		int iftraded = 0;//已经发出的if指令,A50每次交易满一手对冲,瞬间发出if指令
		int filledLast = 0;//最近一次的成交数量
		long idThisTrade;//交易id
		std::vector<rtn> rtnres;//交易结果返回
		int lastpos = -1;//上次检查返回新的vector的数据位置,从-1开始,考虑到0位置前用-1表示
		::EnterCriticalSection(&tdi_a50);
		idThisTrade = clientDlg->PlaceOrder_hedge(false,orderA50);
		clientDlg->m_idrtn.insert(std::pair<long,std::vector<rtn>>(idThisTrade,rtnres));
		::LeaveCriticalSection(&tdi_a50);
		while(true){	
			std::map<long,std::vector<rtn>>::iterator iter;
			std::vector<rtn>::iterator ivec;
			int seconds = 0;//计时
			while(!isA50Validate){
				//设置临界区,防止处理期间的m_idrtn变动
				//每次都要重新获取开始位置,因为map中元素次序会变
				::EnterCriticalSection(&tdi_a50);
				iter = clientDlg->m_idrtn.find(idThisTrade);
				if(iter != clientDlg->m_idrtn.end()){
					ivec = iter->second.begin();
					int size = iter->second.size();
					if(size > 0){
						isA50Validate = true;//有返回消息了
						TRACE("A50 HAS VALIDATED\r\n");
						::LeaveCriticalSection(&tdi_a50);
						break;
					}
				}
				TRACE("A50 NOT VALIDATED\r\n");
				::LeaveCriticalSection(&tdi_a50);
				::Sleep(50);//50毫秒检测一次
				seconds = seconds + 50;
				if(seconds > 100000){//100秒没反应,认为指令送达失败
					//重新发送指令
					::EnterCriticalSection(&tdi_a50);
					idThisTrade = clientDlg->PlaceOrder_hedge(false,orderA50);
					clientDlg->m_idrtn.insert(std::pair<long,std::vector<rtn>>(idThisTrade,rtnres));
					::LeaveCriticalSection(&tdi_a50);
					seconds = 0;//重新计时
				}
			}
			::EnterCriticalSection(&tdi_a50);
			iter = clientDlg->m_idrtn.find(idThisTrade);
			if(iter != clientDlg->m_idrtn.end()){
				ivec = iter->second.begin();
				int size = iter->second.size();
				if(size - 1 > lastpos){
					for(int k = lastpos + 1;k < size;k++){
						if((ivec + k)->status == "Submitted" || 
							(ivec + k)->status == "Filled" || 
							(ivec + k)->status == "ApiCancelled" ||
							(ivec + k)->status == "Cancelled"){
								if((ivec + k)->filled > filledLast){
									int needTradeIf = ((ivec + k)->filled - iftraded * multiply) / multiply;//计算需要新交易的if合约数
									if(needTradeIf >= 1){
										//交易if,生成新的线程
										TRACE("begin%d\r\n",needTradeIf);
										data->numif = needTradeIf;
										::EnterCriticalSection(&ODREF);
										iNextOrderRef++;
										data->orf = iNextOrderRef;
										::LeaveCriticalSection(&ODREF);
										IfInData *indata = new IfInData;
										*indata = *data;
										CWinThread *tradeThread = AfxBeginThread(IfEntry,indata,THREAD_PRIORITY_NORMAL,0,0,NULL);
										handleThread.push_back(tradeThread->m_hThread);
										//更新数据
										iftraded = iftraded + needTradeIf;
									}
									//更新上一次已经成交的数目
									filledLast = (ivec + k)->filled;
								}
								if((ivec + k)->status == "Filled" ||
									(ivec + k)->status == "ApiCancelled" ||
									(ivec + k)->status == "Cancelled"){
										//等待if交易线程结束,进行交易平均成本统计
										//等待所有的IF线程交易完毕,返回
										int nCount = handleThread.size();
										if(nCount >= 1){
											HANDLE * handle = new HANDLE[nCount];
											for(int i = 0 ; i < nCount;i++){
												handle[i] = handleThread[i];
											}
											int nIndex = 0;
											DWORD dwRet = 0;
											dwRet = WaitForMultipleObjects(nCount,handle,true,INFINITE);
											switch(dwRet){
											case WAIT_TIMEOUT:
												TRACE("等待超时,退出检测,因为没有被触发的对象了\r\n");
												break;
											case WAIT_FAILED:
												TRACE("等待失败\r\n");
												break;
											default:
												TRACE("已经全部返回\r\n");
												break;
											}
											delete []handle;
										}
										//统计交易成本,开仓则增加交易成本记录,并返回
										::EnterCriticalSection(&avgPriceOfIf);
										double avgIf = 0;
										std::vector<avgpIf>::iterator iavg;
										double totalvalue = 0;
										int totalnum = 0;
										for(iavg = avgPriceIf.begin();iavg != avgPriceIf.end();iavg++){
											totalvalue = totalvalue + iavg->num * iavg->avgprice;
											totalnum = totalnum + iavg->num;
										}
										::LeaveCriticalSection(&avgPriceOfIf);
										if(totalnum>=1){
											avgIf = totalvalue / totalnum;
											::EnterCriticalSection(&g_index);
											double premium_temp = (ivec + k)->avgFillPrice - avgIf * A50Index / HS300Index
												- A50Index * (lifeOfA50 - clientDlg->lifeOfIf) / 365.0 * 0.0631;//6.31%的无风险套利; 
											::LeaveCriticalSection(&g_index);
											double deviation_temp = premium_temp - datumDiff;
#ifdef _weixin
											CString Price_temp("");
											if(!isflat && isbuy){
												Price_temp.Format("BK:%d,CB:%f,HS300:%f,IF:%f,A50:%f,XINA50:%f\r\n",totalnum,deviation_temp,HS300Index,avgIf,A50Index,(ivec + k)->avgFillPrice);
											}
											else if(!isflat && !isbuy){
												Price_temp.Format("SK:%d,CB:%f,HS300:%f,IF:%f,A50:%f,XINA50:%f\r\n",totalnum,deviation_temp,HS300Index,avgIf,A50Index,(ivec + k)->avgFillPrice);
											}
											else if(isflat && isbuy){
												Price_temp.Format("BP:%d,CB:%f,HS300:%f,IF:%f,A50:%f,XINA50:%f\r\n",totalnum,deviation_temp,HS300Index,avgIf,A50Index,(ivec + k)->avgFillPrice);
											}
											else{
												Price_temp.Format("SP:%d,CB:%f,HS300:%f,IF:%f,A50:%f,XINA50:%f\r\n",totalnum,deviation_temp,HS300Index,avgIf,A50Index,(ivec + k)->avgFillPrice);
											}
											clientDlg->SendMsg(Price_temp);
#endif
											if(!isflat){
												HoldAndDirec hd;
												hd.price = deviation_temp;
												if(!isbuy){
													netHold = netHold - totalnum;
													hd.numDirec = -totalnum;
												}
												else{
													netHold = netHold + totalnum;
													hd.numDirec = totalnum;
												}	
												holdHedge.push_back(hd);
											}
										}
										//删除这次交易ID对应的键值
										clientDlg->m_idrtn.erase(iter);
										TRACE("对冲结束,准备脱离临界区\r\n");
										::LeaveCriticalSection(&tdi_a50);
										delete data;
										TRACE("对冲结束,返回0值\r\n");
										return 0;
								}
						}			
						else{
							//NOTHING TO DO
						}
					}
					lastpos = size -1;
				}
			}
			::LeaveCriticalSection(&tdi_a50);
			UpdateTrade.Lock(INFINITE);//等待同步事件击发
			//判断价格是否合理,否则修改A50合约
			calDeviation();//重新计算偏差 
			::EnterCriticalSection(&g_A50Price);
			if(isbuy){
				if(deviationHigh <= deviationHigh_save - 5.0){
					PUT(lmtPrice,a50Ask1);
					clientDlg->ModifyOrder_hedge(idThisTrade,orderA50);
				}
				else if(GET(lmtPrice) < a50Bid1){
					PUT(lmtPrice,a50Bid1);
					clientDlg->ModifyOrder_hedge(idThisTrade,orderA50);
				}
			}
			else{
				if(deviationLow >= deviationLow_save + 5.0){
					PUT(lmtPrice,a50Bid1);
					clientDlg->ModifyOrder_hedge(idThisTrade,orderA50);
				}
				else if(GET(lmtPrice) > a50Ask1){
					PUT(lmtPrice,a50Ask1);	
					clientDlg->ModifyOrder_hedge(idThisTrade,orderA50);
				}
			}
			::LeaveCriticalSection(&g_A50Price);
		}
		delete data;
		return 0;
#undef PUT
#undef GET
	}
	else{
		int needTradeIf = numofIf;
		if(needTradeIf >= 1){
			//交易if,生成新的线程
			TRACE("begin%d\r\n",needTradeIf);
			data->numif = needTradeIf;
			::EnterCriticalSection(&ODREF);
			iNextOrderRef++;
			data->orf = iNextOrderRef;
			::LeaveCriticalSection(&ODREF);
			IfInData *indata = new IfInData;
			*indata = *data;
			CWinThread *tradeThread = AfxBeginThread(IfEntry,indata,THREAD_PRIORITY_NORMAL,0,0,NULL);
			handleThread.push_back(tradeThread->m_hThread);
		}
		int nCount = handleThread.size();
		if(nCount >= 1){
			HANDLE * handle = new HANDLE[nCount];
			for(int i = 0 ; i < nCount;i++){
				handle[i] = handleThread[i];
			}
			int nIndex = 0;
			DWORD dwRet = 0;
			dwRet = WaitForMultipleObjects(nCount,handle,true,INFINITE);
			switch(dwRet){
			case WAIT_TIMEOUT:
				TRACE("等待超时,退出检测,因为没有被触发的对象了\r\n");
				break;
			case WAIT_FAILED:
				TRACE("等待失败\r\n");
				break;
			default:
				TRACE("已经全部返回\r\n");
				break;
			}
			delete []handle;
		}
		//统计交易成本,开仓则增加交易成本记录,并返回
		::EnterCriticalSection(&avgPriceOfIf);
		double avgIf = 0;
		std::vector<avgpIf>::iterator iavg;
		double totalvalue = 0;
		int totalnum = 0;
		double avgFillPriceA50 = 0;
		if(isbuy){
			avgFillPriceA50 = a50Ask1;
		}
		else{
			avgFillPriceA50 = a50Bid1;
		}
		for(iavg = avgPriceIf.begin();iavg != avgPriceIf.end();iavg++){
			totalvalue = totalvalue + iavg->num * iavg->avgprice;
			totalnum = totalnum + iavg->num;
		}
		::LeaveCriticalSection(&avgPriceOfIf);
		if(totalnum>=1){
			avgIf = totalvalue / totalnum;
			::EnterCriticalSection(&g_index);
			double premium_temp = avgFillPriceA50 - avgIf * A50Index / HS300Index
				- A50Index * (lifeOfA50 - clientDlg->lifeOfIf) / 365.0 * 0.0631;//6.31%的无风险套利; 
			::LeaveCriticalSection(&g_index);
			double deviation_temp = premium_temp - datumDiff;
#ifdef _weixin
			CString Price_temp("");
			if(!isflat && isbuy){
				Price_temp.Format("BK:%d,CB:%f,HS300:%f,IF:%f,A50:%f,XINA50:%f\r\n",totalnum,deviation_temp,HS300Index,avgIf,A50Index,avgFillPriceA50);
			}
			else if(!isflat && !isbuy){
				Price_temp.Format("SK:%d,CB:%f,HS300:%f,IF:%f,A50:%f,XINA50:%f\r\n",totalnum,deviation_temp,HS300Index,avgIf,A50Index,avgFillPriceA50);
			}
			else if(isflat && isbuy){
				Price_temp.Format("BP:%d,CB:%f,HS300:%f,IF:%f,A50:%f,XINA50:%f\r\n",totalnum,deviation_temp,HS300Index,avgIf,A50Index,avgFillPriceA50);
			}
			else{
				Price_temp.Format("SP:%d,CB:%f,HS300:%f,IF:%f,A50:%f,XINA50:%f\r\n",totalnum,deviation_temp,HS300Index,avgIf,A50Index,avgFillPriceA50);
			}
			clientDlg->SendMsg(Price_temp);
#endif
			if(!isflat){
				HoldAndDirec hd;
				hd.price = deviation_temp;
				if(!isbuy){
					netHold = netHold - totalnum;
					hd.numDirec = -totalnum;
				}
				else{
					netHold = netHold + totalnum;
					hd.numDirec = totalnum;
				}	
				holdHedge.push_back(hd);
			}
		}
		TRACE("对冲结束,准备脱离临界区\r\n");
		::LeaveCriticalSection(&tdi_a50);
		delete data;
		TRACE("对冲结束,返回0值\r\n");
		return 0;
	}
}
Beispiel #4
0
UINT TradeEntry_01(LPVOID pParam)//交易线程1改版
{
#define NUMLADDER 11
	double ladder_01[NUMLADDER] = {-100,-80,-60,-40,-20,0,20,40,60,80,100};//暂时设11档,一定要正负对称且呈阶梯状,否则逻辑混乱
	int needAmount_01[NUMLADDER] = {5,4,3,2,1,0,-1,-2,-3,-4,-5};//每档对应的持仓数量
	int holdA50_01 = 0;//A50持有数量
	int holdIf_01 = 0;//IF持有数量
	int needHoldA50_01 = 0;//A50应该持有数量
	int needHoldIf_01 = 0;//IF应该持有数量
	int nowLadder_01 = 0;//当前梯级
	bool isFirst = true;//第一次操作
	bool isFilledSectionLeft = false;//本区间左侧目标位的买卖操作是否完成
	bool isFilledSectionRight = false;//本区间右侧目标位的买卖操作是否完成
	int nowSection = 4444;//当前所在的区间,由左端点决定,取4444的初值表示还未找到区间
	if(clientDlg == NULL){
		return -1;
	}
	if(pUserApi == NULL){
		return -1;
	}	
	//从对话框初始化
	datumDiff = clientDlg->m_DeltaDatumDiff + clientDlg->m_datumDiff;
#ifdef _debug 
	holdA50_01 = 50;
#endif
	while(true){
		UpdateTrade.Lock(INFINITE);//事件触发
		//获取系统时间
		SYSTEMTIME sys;
		GetLocalTime(&sys);
		CString PREMIUM;	
		calDeviation();
		deviationHigh_save = deviationHigh;
		deviationLow_save = deviationLow;
		PREMIUM.Format(_T("%.4f"),premiumLow);	
		clientDlg->SetDlgItemTextA(IDC_EDIT18,PREMIUM);
		PREMIUM.Format(_T("%.4f"),premiumHigh);	
		clientDlg->SetDlgItemTextA(IDC_EDIT16,PREMIUM);
		//非交易日返回
		if(!isTradeDay(sys.wYear,sys.wMonth,sys.wDay))
		{
			continue;
		}
		//非常规交易时间
		if((sys.wHour == 9 && sys.wMinute < 10) || 
			(sys.wHour == 15 && sys.wMinute > 15) ||
			(sys.wHour == 11 && sys.wMinute > 30) ||
			(sys.wHour == 12)||
			(sys.wHour < 9) || (sys.wHour > 15)){
				continue;
		}
		if(clientDlg->tradeEnd){//终止
			//做清空处理,重新启动时会初始化
			return -1;
		}
		if(clientDlg->stop){//暂停
			continue;
		}
		if(_isnan(datumDiff) != 0 || _isnan(premium)!=0 ||_isnan(deviation)!=0){
			continue;//判断非零值错误
		}
		if(deviationHigh >= 100 || deviationLow <= -100){
			continue;//超过范围,返回
		}
		for(int i = 0;i <= NUMLADDER - 1;i++){//计算当前的区间位置
			if(deviationLow >= ladder_01[i] && deviationHigh <= ladder_01[i + 1]){
				if(isFirst){
					nowSection = i;
					isFirst = false;
					break;
				}
				else{
					if(nowSection != i){
						nowSection = i;
						break;
					}
				}
			}
		}
		if(nowSection == 4444){
			continue;//还未找到区间,返回重新寻找
		}
		bool isFilledL = false,isFilledR = false;
		int needA50L = 0,needA50R = 0;
		int needIfL = 0,needIfR = 0;
		needIfL = -needAmount_01[nowSection];
		needIfR = -needAmount_01[nowSection + 1];
		needA50L = needAmount_01[nowSection] * multiply;
		needA50R = needAmount_01[nowSection + 1] * multiply;
		//强平
		if(holdA50_01 > needA50L){
			//FTA50(holdA50_01 - needA50L,false);
			holdA50_01 = needA50L;
		}
		if(holdIf_01 < needIfL){
			//FTIF(needIfL - holdIf_01,true);
			holdIf_01 = needIfL;
		}
		if(holdA50_01 < needA50R){
			//FTA50(needA50R - holdA50_01,true);
			holdA50_01 = needA50R;
		}
		if(holdIf_01 > needIfR){
			//FTIF(holdIf_01 - needIfR,false);
			holdIf_01 = needIfR;
		}
		//查询a50账户可用资金
		//

		if(nowSection < (NUMLADDER - 1) / 2){
			if(holdA50_01 < needA50L || holdIf_01 < needIfL){
				isFilledL = false;
			}
			if(holdA50_01 < needA50R || holdIf_01 < needIfR){
				isFilledR = false;
			} 
		}

		/*
		if(deviation <= (ladder_01[nowSection] + ladder_01[nowSection + 1]) / 2.0){
		double A50Price = ladder_01[nowSection] + datumDiff + ifBid1 * A50Index / HS300Index + A50Index * dltInterest;
		buyOrSell_01(holdA50_01,holdIf_01,needAmount_01[nowSection] * multiply,true);
		}
		else{
		double A50Price = ladder_01[nowSection + 1] + datumDiff + ifAsk1 * A50Index / HS300Index + A50Index * dltInterest;
		buyOrSell_01(holdA50_01,holdIf_01,needAmount_01[nowSection + 1] * multiply,false);
		}
		*/
	}
	return 0;
}
Beispiel #5
0
//只能开启一个交易线程,否则同步可能出现问题
UINT TradeEntry_00(LPVOID pParam)//启动入口,作为一个独立的线程
{
	CThostFtdcQryInstrumentField req;
	memset(&req, 0, sizeof(req));
	strcpy(req.InstrumentID, INSTRUMENT_ID);
	::EnterCriticalSection(&REQUEST_ID_IF);
	int iResult = pUserApi->ReqQryInstrument(&req, ++iRequestID);
	::LeaveCriticalSection(&REQUEST_ID_IF);

	CThostFtdcQryInvestorPositionField req00;
	memset(&req00, 0, sizeof(req00));
	strcpy(req00.BrokerID, BROKER_ID);
	strcpy(req00.InvestorID, INVESTOR_ID);
	strcpy(req00.InstrumentID, INSTRUMENT_ID);
	::EnterCriticalSection(&REQUEST_ID_IF);
	iResult = pUserApi->ReqQryInvestorPosition(&req00, ++iRequestID);
	::LeaveCriticalSection(&REQUEST_ID_IF);

#ifdef _debug
	iNextOrderRef++;//测试
	ifAsk1 = 2180;//
	IfInData *data;//测试
	data = new IfInData(1,false,true,iNextOrderRef); //测试
	AfxBeginThread(IfEntry,data,THREAD_PRIORITY_NORMAL,0,0,NULL);//测试
	return 0;//测试
#endif
	if(clientDlg == NULL){
		return -1;
	}
	if(pUserApi == NULL){
		return -1;
	}	
	//从对话框初始化
	step = clientDlg->m_step;
	multiply = clientDlg->m_multiply;
	aimOfLadder = clientDlg->m_aimOfLadder;
	datumDiff = clientDlg->m_DeltaDatumDiff + clientDlg->m_datumDiff;
	HoldAndDirec tempIni;
	tempIni.price = clientDlg->m_costINI - datumDiff;//持仓相对价格
	tempIni.numDirec = clientDlg->m_numINI;//带有方向的持仓
	holdHedge.push_back(tempIni);
	netHold = tempIni.numDirec;
	//溢价和基差计算
	while(true){
		UpdateTrade.Lock(INFINITE);//事件触发
		//获取系统时间
		//SYSTEMTIME sys;
		//GetLocalTime(&sys);
		CString PREMIUM;	
		calDeviation();
		deviationHigh_save = deviationHigh;
		deviationLow_save = deviationLow;
		PREMIUM.Format(_T("%.4f"),premiumLow);	
		clientDlg->SetDlgItemTextA(IDC_EDIT18,PREMIUM);
		PREMIUM.Format(_T("%.4f"),premiumHigh);	
		clientDlg->SetDlgItemTextA(IDC_EDIT16,PREMIUM);
		/*
		//非交易日返回
		if(!isTradeDay(sys.wYear,sys.wMonth,sys.wDay))
		{
		continue;
		}
		//非常规交易时间
		if((sys.wHour == 9 && sys.wMinute < 10) || 
		(sys.wHour == 15 && sys.wMinute > 15) ||
		(sys.wHour == 11 && sys.wMinute > 30) ||
		(sys.wHour == 12)||
		(sys.wHour < 9) || (sys.wHour > 15)){
		continue;
		}
		*/
		if(clientDlg->tradeEnd){//终止
			//做清空处理,重新启动时会初始化
			holdHedge.clear();
			netHold = 0;
			return -1;
		}
		if(clientDlg->stop){//暂停
			continue;
		}
		if(_isnan(datumDiff) != 0 || _isnan(premium)!=0 ||_isnan(deviation)!=0){
			continue;//判断非零值错误
		}
		::EnterCriticalSection(&g_A50Price);
		::EnterCriticalSection(&g_IfPrice);
		::EnterCriticalSection(&g_index);
		if(a50Bid1 < 1 || a50Ask1 < 1 || ifAsk1 < 1 || ifBid1 < 1 || A50Index < 1 || HS300Index < 1){
			::LeaveCriticalSection(&g_IfPrice);
			::LeaveCriticalSection(&g_A50Price);
			::LeaveCriticalSection(&g_index);;
			continue;
		}
		else{
			::LeaveCriticalSection(&g_IfPrice);
			::LeaveCriticalSection(&g_A50Price);
			::LeaveCriticalSection(&g_index);
		}
		if(fabs(premium) > 300 || fabs(premium) < 0.01){
			continue;//排除开盘时有可能报价不全导致的错误溢价计算
		}
		if(deviation >= 0){
#ifdef _case1
			//临时用multiply代替需要的合约数目,因为现在只有一手,保证成交
			if(a50Bid1Size >= multiply * 1){
				ladder = (int)(deviationLow / step);
			}
			else{
				continue;
			}
#else
			ladder = (int)((deviationLow + 2.5) / step);
#endif
		}
		else{
#ifdef _case1
			//临时用multiply代替需要的合约数目,因为现在只有一手,保证成交
			if(a50Ask1Size >= multiply * 1){
				ladder = -(int)(-deviationHigh / step);
			}
			else{
				continue;
			}
#else
			ladder = -(int)((-deviationHigh + 2.5) / step);
#endif
		}
		if(ladder > 1){
			ladder = 1;
		}
		else if(ladder < -1){
			ladder = -1;
		}
		needHold = aimOfLadder * ladder;//需要的合约与偏差的关系,可以根据资金量进行修改
#ifdef _case1
		profitTarget = step;
#else
		profitTarget = step - 2.5;
#endif
		double profitUnit = 0;
		int needBuyFlat = 0,needSellFlat = 0;//始终大于0的,无正负
		double totalTradingValue = 0;//准备交易的总价值
		for(unsigned int j = 0;j < holdHedge.size();j++){
			itHedge = holdHedge.begin() + j;
			//if(itHedge->numDirec < 0){//其实只要nethold为负,就保证了所有的numDirec为负,不存在既有numDirec为正,又有为负的情况
			if(netHold < 0){
				profitUnit = itHedge->price - deviationHigh;
				if(profitUnit >= profitTarget){
					needBuyFlat = needBuyFlat - itHedge->numDirec;
					totalTradingValue = totalTradingValue + itHedge->price * (-itHedge->numDirec);
					//更新记录
					netHold = netHold - itHedge->numDirec;
					holdHedge.erase(itHedge);
					j--;//出现删除操作时,需要将指针向前倒退
				}
			}
			//else if(itHedge->numDirec > 0)
			else if(netHold > 0){
				profitUnit = -(itHedge->price - deviationLow);
				if(profitUnit >= profitTarget){
					needSellFlat = needSellFlat + itHedge->numDirec;
					totalTradingValue = totalTradingValue + itHedge->price * itHedge->numDirec;
					//更新记录
					netHold = netHold - itHedge->numDirec;
					holdHedge.erase(itHedge);
					j--;
				}
			}
			else{
				//等于0时什么也不做
			}
		}
		//平仓操作,,其实买平和卖平一定只有一个得到执行的,否则便出现了问题
		flatOrOpen(needBuyFlat,true,true);
		flatOrOpen(needSellFlat,false,true);
		//开仓操作
		BS(needHold,netHold);
	}
	return 0;//根本走不到这儿
}