Database.cpp
上传用户:zhanglf88
上传日期:2013-11-19
资源大小:6036k
文件大小:21k
源码类别:

金融证券系统

开发平台:

Visual C++

  1. /*
  2. Cross Platform Core Code.
  3. Copyright(R) 2001-2002 Balang Software.
  4. All rights reserved.
  5. Using:
  6. DllMain( HANDLE, DWORD, LPVOID );
  7. class CStDatabase;
  8. */
  9. #include "StdAfx.h"
  10. #include "../Include/Database.h"
  11. #include "../Include/SpString.h"
  12. #include <direct.h>
  13. #include "SelfDB.h"
  14. #ifdef _DEBUG
  15. #define new DEBUG_NEW
  16. #undef THIS_FILE
  17. static char THIS_FILE[] = __FILE__;
  18. #endif
  19. ////////////////////////////////////////////////////////////////////////////////////////////
  20. // convertor
  21. BOOL convert_TYDAY_RECORD_to_KDATA( TYDAY_RECORD * precord, KDATA * pkd )
  22. {
  23. SP_ASSERT( precord && pkd );
  24. if( NULL == precord || NULL == pkd )
  25. return FALSE;
  26. memset( pkd, 0, sizeof(KDATA) );
  27. pkd->m_dwMarket = CStock::marketUnknown;
  28. strncpy( pkd->m_szCode, precord->code, min(sizeof(pkd->m_szCode)-1,sizeof(precord->code)) );
  29. pkd->m_date = precord->date;
  30. CSPTime sptime;
  31. if( sptime.FromStockTimeDay(pkd->m_date) )
  32. pkd->m_time = sptime.GetTime();
  33. pkd->m_fOpen = (float)( precord->open * 0.001 );
  34. pkd->m_fHigh = (float)( precord->high * 0.001 );
  35. pkd->m_fLow = (float)( precord->low * 0.001 );
  36. pkd->m_fClose = (float)( precord->close * 0.001 );
  37. pkd->m_fAmount = (float)( precord->amount * 1000. );
  38. pkd->m_fVolume = (float)( precord->volume * 100. );
  39. return TRUE;
  40. }
  41. BOOL convert_TYDAY_RECORD_MIN_to_KDATA( TYDAY_RECORD * precord, KDATA * pkd )
  42. {
  43. SP_ASSERT( precord && pkd );
  44. if( NULL == precord || NULL == pkd )
  45. return FALSE;
  46. memset( pkd, 0, sizeof(KDATA) );
  47. pkd->m_dwMarket = CStock::marketUnknown;
  48. strncpy( pkd->m_szCode, precord->code, min(sizeof(pkd->m_szCode)-1,sizeof(precord->code)) );
  49. pkd->m_date = precord->date;
  50. CSPTime sptime;
  51. if( sptime.FromStockTimeDay(pkd->m_date) )
  52. pkd->m_time = sptime.GetTime();
  53. pkd->m_fOpen = (float)( precord->open * 0.001 );
  54. pkd->m_fHigh = (float)( precord->high * 0.001 );
  55. pkd->m_fLow = (float)( precord->low * 0.001 );
  56. pkd->m_fClose = (float)( precord->close * 0.001 );
  57. pkd->m_fAmount = (float)( precord->amount * 100. );
  58. pkd->m_fVolume = (float)( precord->volume * 100. );
  59. return TRUE;
  60. }
  61. BOOL convert_KDATA_to_TYDAY_RECORD( DWORD dwSerial, const char * name, KDATA * pkd, TYDAY_RECORD * precord )
  62. {
  63. SP_ASSERT( precord && pkd );
  64. if( NULL == precord || NULL == pkd )
  65. return FALSE;
  66. memset( precord, 0, sizeof(TYDAY_RECORD) );
  67. precord->magic = 0x06;
  68. precord->magic2 = 0x08;
  69. strncpy( precord->code, pkd->m_szCode, min(sizeof(precord->code),sizeof(pkd->m_szCode)) );
  70. if( name )
  71. strncpy( precord->name, name, min(sizeof(precord->name),strlen(name)) );
  72. precord->date = pkd->m_date;
  73. precord->open = (DWORD)( pkd->m_fOpen * 1000 );
  74. precord->high = (DWORD)( pkd->m_fHigh * 1000 );
  75. precord->low = (DWORD)( pkd->m_fLow * 1000 );
  76. precord->close = (DWORD)( pkd->m_fClose * 1000 );
  77. precord->amount = (DWORD)( pkd->m_fAmount * 0.001 );
  78. precord->volume = (DWORD)( pkd->m_fVolume * 0.01 );
  79. precord->serial = dwSerial;
  80. return TRUE;
  81. }
  82. BOOL convert_KDATA_to_TYDAY_RECORD_MIN( DWORD dwSerial, const char * name, KDATA * pkd, TYDAY_RECORD * precord )
  83. {
  84. SP_ASSERT( precord && pkd );
  85. if( NULL == precord || NULL == pkd )
  86. return FALSE;
  87. memset( precord, 0, sizeof(TYDAY_RECORD) );
  88. precord->magic = 0x06;
  89. precord->magic2 = 0x08;
  90. strncpy( precord->code, pkd->m_szCode, min(sizeof(precord->code),sizeof(pkd->m_szCode)) );
  91. if( name )
  92. strncpy( precord->name, name, min(sizeof(precord->name),strlen(name)) );
  93. precord->date = pkd->m_date;
  94. precord->open = (DWORD)( pkd->m_fOpen * 1000 );
  95. precord->high = (DWORD)( pkd->m_fHigh * 1000 );
  96. precord->low = (DWORD)( pkd->m_fLow * 1000 );
  97. precord->close = (DWORD)( pkd->m_fClose * 1000 );
  98. precord->amount = (DWORD)( pkd->m_fAmount * 0.01 );
  99. precord->volume = (DWORD)( pkd->m_fVolume * 0.01 );
  100. precord->serial = dwSerial;
  101. return TRUE;
  102. }
  103. BOOL convert_FXJDAY_RECORD_to_KDATA( DWORD dwMarket, LPCTSTR lpszCode, int nKType, FXJDAY_RECORD *precord, KDATA *pkd )
  104. {
  105. SP_ASSERT( precord && pkd && lpszCode );
  106. if( NULL == precord || NULL == pkd )
  107. return FALSE;
  108. memset( pkd, 0, sizeof(KDATA) );
  109. pkd->m_dwMarket = dwMarket;
  110. strncpy( pkd->m_szCode, lpszCode, min(sizeof(pkd->m_szCode)-1,strlen(lpszCode)) );
  111. pkd->m_time = precord->m_time;
  112. CSPTime sptime(pkd->m_time);
  113. pkd->m_date = sptime.ToStockTime( CKData::IsDayOrMin(nKType) );
  114. pkd->m_fOpen = precord->open;
  115. pkd->m_fHigh = precord->high;
  116. pkd->m_fLow = precord->low;
  117. pkd->m_fClose = precord->close;
  118. pkd->m_fAmount = precord->amount;
  119. pkd->m_fVolume = (float)( precord->volume * 100. );
  120. return TRUE;
  121. }
  122. ////////////////////////////////////////////////////////////////////////////////////////////
  123. // class CStDatabase
  124. CStDatabase::CStDatabase()
  125. {
  126. m_pStore = NULL;
  127. }
  128. CStDatabase::~CStDatabase()
  129. {
  130. if( m_pStore )
  131. {
  132. delete m_pStore;
  133. m_pStore = NULL;
  134. }
  135. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  136. {
  137. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  138. if( pStore )
  139. delete pStore;
  140. }
  141. m_aptrAssistant.RemoveAll();
  142. }
  143. BOOL CStDatabase::CreateSelfDB( const char * rootpath )
  144. {
  145. return CSelfDB::CreateSelfDB( rootpath );
  146. }
  147. int CStDatabase::IsValidDataType ( int nType )
  148. {
  149. return IStStore::IsValidDataType( nType );
  150. }
  151. int CStDatabase::GetSupportedDataType ( CDBType * pdbtype, int maxsize )
  152. {
  153. return IStStore::GetSupportedDataType( pdbtype, maxsize );
  154. }
  155. BOOL CStDatabase::SetRootPath( const char * rootpath, int nDBType )
  156. {
  157. if( m_pStore )
  158. delete m_pStore;
  159. m_pStore = IStStore::CreateStore( rootpath, nDBType );
  160. return (NULL != m_pStore);
  161. }
  162. BOOL CStDatabase::IsOK( )
  163. { return m_pStore && m_pStore->IsOK(); }
  164. const char *CStDatabase::GetRootPath( )
  165. { if(!IsOK()) return NULL; return m_pStore->GetRootPath(); }
  166. int CStDatabase::GetDBType( )
  167. { if(!IsOK()) return IStStore::dbtypeUnknown; return m_pStore->GetDBType(); }
  168. const char *CStDatabase::GetDBTypeName( )
  169. { if(!IsOK()) return NULL; return m_pStore->GetDBTypeName(); }
  170. DWORD CStDatabase::GetSelfTempPath( char *szTempPath, int size )
  171. {
  172. const char *szRoot = GetRootPath();
  173. if( 0 == strlen( szRoot ) )
  174. {
  175. if( NULL != szTempPath && size > 0 )
  176. szTempPath[0] = '';
  177. return 0;
  178. }
  179. char szReturn[MAX_PATH+1];
  180. memset( szReturn, 0, sizeof(szReturn) );
  181. strncpy( szReturn, szRoot, MAX_PATH );
  182. strncat( szReturn, "temp", MAX_PATH-strlen(szReturn) );
  183. strncat( szReturn, STRING_DIRSEP, MAX_PATH-strlen(szReturn) );
  184. BOOL bCreated = TRUE;
  185. if( 0 != access(szReturn,0) )
  186. bCreated = (0==_mkdir(szReturn));
  187. if( !bCreated )
  188. {
  189. if( NULL != szTempPath && size > 0 )
  190. szTempPath[0] = '';
  191. return 0;
  192. }
  193. strncpy( szTempPath, szReturn, size );
  194. return strlen(szReturn);
  195. }
  196. BOOL CStDatabase::GetLastErrorMessage(LPTSTR lpszError, UINT nMaxError)
  197. {
  198. if( nMaxError > 0 )
  199. lpszError[0] = '';
  200. return FALSE;
  201. }
  202. int CStDatabase::GetMaxStockNumber( )
  203. {
  204. if(!IsOK()) return 0;
  205. int nSize = m_pStore->GetMaxStockNumber();
  206. if( nSize > 0 )
  207. return nSize;
  208. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  209. {
  210. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  211. nSize = pStore->GetMaxStockNumber();
  212. if( nSize > 0 )
  213. return nSize;
  214. }
  215. return nSize;
  216. }
  217. int CStDatabase::LoadCodetable( CStockContainer & container )
  218. {
  219. if(!IsOK()) return 0;
  220. int nSize = m_pStore->LoadCodetable( container );
  221. if( nSize > 0 )
  222. return nSize;
  223. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  224. {
  225. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  226. nSize = pStore->LoadCodetable( container );
  227. if( nSize > 0 )
  228. return nSize;
  229. }
  230. return nSize;
  231. }
  232. int CStDatabase::StoreCodetable( CStockContainer & container )
  233. { if(!IsOK()) return 0; return m_pStore->StoreCodetable( container ); }
  234. int CStDatabase::LoadKDataCache( CStockContainer & container, PROGRESS_CALLBACK fnCallback, void *cookie, int nProgStart, int nProgEnd )
  235. {
  236. if(!IsOK()) return 0;
  237. int nSize = m_pStore->LoadKDataCache( container, fnCallback, cookie, nProgStart, nProgEnd );
  238. if( nSize > 0 )
  239. return nSize;
  240. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  241. {
  242. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  243. nSize = pStore->LoadKDataCache( container, fnCallback, cookie, nProgStart, nProgEnd );
  244. if( nSize > 0 )
  245. return nSize;
  246. }
  247. return nSize;
  248. }
  249. int CStDatabase::LoadBasetable( CStockContainer & container )
  250. { if(!IsOK()) return 0; return m_pStore->LoadBasetable( container ); }
  251. int CStDatabase::StoreBasetable( CStockContainer & container )
  252. { if(!IsOK()) return 0; return m_pStore->StoreBasetable( container ); }
  253. int CStDatabase::LoadBaseText( CStock *pstock )
  254. {
  255. if( !pstock || !IsOK() ) return 0;
  256. int nSize = m_pStore->LoadBaseText( pstock );
  257. if( nSize > 0 )
  258. return nSize;
  259. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  260. {
  261. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  262. CStock stock;
  263. stock.SetStockInfo( &(pstock->GetStockInfo()) );
  264. if( pStore && pStore->LoadBaseText( &stock ) > 0 )
  265. {
  266. nSize = pstock->MergeBaseText( stock );
  267. }
  268. }
  269. return nSize;
  270. }
  271. int CStDatabase::LoadKData( CStock *pstock, int period )
  272. {
  273. if( !pstock || !IsOK()) return 0;
  274. int nSize = m_pStore->LoadKData( pstock, period );
  275. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  276. {
  277. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  278. CStock stock;
  279. stock.SetStockInfo( &(pstock->GetStockInfo()) );
  280. if( pStore->LoadKData( &stock, period ) > 0 )
  281. {
  282. nSize = pstock->MergeKData( stock, period );
  283. }
  284. }
  285. return nSize;
  286. }
  287. int CStDatabase::LoadDRData( CStock *pstock )
  288. {
  289. if( !pstock || !IsOK() )
  290. return 0;
  291. int nSize = m_pStore->LoadDRData( pstock );
  292. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  293. {
  294. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  295. CStock stock;
  296. stock.SetStockInfo( &(pstock->GetStockInfo()) );
  297. if( pStore && pStore->LoadDRData( &stock ) > 0 )
  298. {
  299. nSize = pstock->MergeDRData( stock );
  300. }
  301. }
  302. return nSize;
  303. }
  304. int CStDatabase::StoreDRData( CStock *pstock )
  305. { if(!IsOK()) return 0;
  306. return m_pStore->StoreDRData( pstock ); }
  307. int CStDatabase::LoadReport( CStock *pstock )
  308. {
  309. if( !pstock || !IsOK() ) return 0;
  310. int nSize = m_pStore->LoadReport( pstock );
  311. if( nSize > 0 )
  312. return nSize;
  313. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  314. {
  315. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  316. if( pStore )
  317. nSize = pStore->LoadReport( pstock );
  318. if( nSize > 0 )
  319. return nSize;
  320. }
  321. return nSize;
  322. }
  323. int CStDatabase::LoadMinute( CStock *pstock )
  324. {
  325. if( !pstock || !IsOK() ) return 0;
  326. int nSize = m_pStore->LoadMinute( pstock );
  327. if( nSize > 0 )
  328. return nSize;
  329. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  330. {
  331. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  332. if( pStore )
  333. nSize = pStore->LoadMinute( pstock );
  334. if( nSize > 0 )
  335. return nSize;
  336. }
  337. return nSize;
  338. }
  339. int CStDatabase::LoadOutline( CStock *pstock )
  340. {
  341. if( !pstock || !IsOK() ) return 0;
  342. int nSize = m_pStore->LoadOutline( pstock );
  343. if( nSize > 0 )
  344. return nSize;
  345. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  346. {
  347. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  348. if( pStore )
  349. nSize = pStore->LoadOutline( pstock );
  350. if( nSize > 0 )
  351. return nSize;
  352. }
  353. return nSize;
  354. }
  355. int CStDatabase::StoreReport( REPORT * pReport, int nCount, BOOL bBigTrade )
  356. { if(!IsOK()) return 0;
  357. return m_pStore->StoreReport( pReport, nCount, bBigTrade ); }
  358. int CStDatabase::StoreMinute( MINUTE * pMinute, int nCount )
  359. { if(!IsOK()) return 0;
  360. return m_pStore->StoreMinute( pMinute, nCount ); }
  361. int CStDatabase::StoreOutline( OUTLINE * pOutline, int nCount )
  362. { if(!IsOK()) return 0;
  363. return m_pStore->StoreOutline( pOutline, nCount ); }
  364. int CStDatabase::InstallCodetbl( const char * filename, const char *orgname )
  365. { if(!IsOK()) return 0;
  366. return m_pStore->InstallCodetbl( filename, orgname ); }
  367. int CStDatabase::InstallCodetblBlock( const char * filename, const char *orgname )
  368. { if(!IsOK()) return 0;
  369. return m_pStore->InstallCodetblBlock( filename, orgname ); }
  370. int CStDatabase::InstallCodetblFxjBlock( const char * filename, const char *orgname )
  371. { if(!IsOK()) return 0;
  372. return m_pStore->InstallCodetblFxjBlock( filename, orgname ); }
  373. int CStDatabase::InstallKData( CKData &kdata, BOOL bOverwrite )
  374. { if(!IsOK()) return 0;
  375. return m_pStore->InstallKData( kdata, bOverwrite ); }
  376. int CStDatabase::InstallKDataTy( const char * stkfile, int ktype, PROGRESS_CALLBACK fnCallback, void *cookie )
  377. { if(!IsOK()) return 0;
  378. return m_pStore->InstallKDataTy( stkfile, ktype, fnCallback, cookie ); }
  379. int CStDatabase::InstallKDataFxj( const char * dadfile, int ktype, PROGRESS_CALLBACK fnCallback, void *cookie )
  380. { if(!IsOK()) return 0;
  381. return m_pStore->InstallKDataFxj( dadfile, ktype, fnCallback, cookie ); }
  382. int CStDatabase::InstallDRData( CDRData &drdata )
  383. { if(!IsOK()) return 0;
  384. return m_pStore->InstallDRData( drdata ); }
  385. int CStDatabase::InstallDRDataClk( const char * filename, const char *orgname )
  386. { if(!IsOK()) return 0;
  387. return m_pStore->InstallDRDataClk( filename, orgname ); }
  388. int CStDatabase::InstallDRDataFxj( const char * fxjfilename )
  389. { if(!IsOK()) return 0;
  390. return m_pStore->InstallDRDataFxj( fxjfilename ); }
  391. int CStDatabase::InstallBasetable( const char * filename, const char *orgname )
  392. { if(!IsOK()) return 0;
  393. return m_pStore->InstallBasetable( filename, orgname ); }
  394. int CStDatabase::InstallBasetableTdx( const char * filename )
  395. { if(!IsOK()) return 0;
  396. return m_pStore->InstallBasetableTdx( filename ); }
  397. int CStDatabase::InstallBasetableFxj( const char * filename )
  398. { if(!IsOK()) return 0;
  399. return m_pStore->InstallBasetableFxj( filename ); }
  400. int CStDatabase::InstallBaseText( const char * filename, const char *orgname )
  401. { if(!IsOK()) return 0;
  402. return m_pStore->InstallBaseText( filename, orgname ); }
  403. int CStDatabase::InstallBaseText( const char * buffer, int nLen, const char *orgname )
  404. { if(!IsOK()) return 0;
  405. return m_pStore->InstallBaseText( buffer, nLen, orgname ); }
  406. int CStDatabase::InstallNewsText( const char * filename, const char *orgname )
  407. { if(!IsOK()) return 0;
  408. return m_pStore->InstallNewsText( filename, orgname ); }
  409. int CStDatabase::InstallNewsText( const char * buffer, int nLen, const char *orgname )
  410. { if(!IsOK()) return 0;
  411. return m_pStore->InstallNewsText( buffer, nLen, orgname ); }
  412. BOOL CStDatabase::AddAssistantRootPath( const char * rootpath, int nDBType )
  413. {
  414. IStStore * pStore = IStStore::CreateStore( rootpath, nDBType );
  415. if( NULL == pStore )
  416. return FALSE;
  417. m_aptrAssistant.Add( pStore );
  418. return TRUE;
  419. }
  420. void CStDatabase::RemoveAssistant( const char * rootpath )
  421. {
  422. if( NULL == rootpath || strlen(rootpath) == 0 )
  423. return;
  424. for( int i=m_aptrAssistant.GetSize()-1; i>=0; i-- )
  425. {
  426. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  427. if( pStore && 0 == strcmp( pStore->GetRootPath(), rootpath ) )
  428. {
  429. m_aptrAssistant.RemoveAt(i);
  430. delete pStore;
  431. }
  432. }
  433. }
  434. void CStDatabase::RemoveAllAssistant( )
  435. {
  436. for( int i=0; i<m_aptrAssistant.GetSize(); i++ )
  437. {
  438. IStStore * pStore = (IStStore *)m_aptrAssistant.ElementAt(i);
  439. if( pStore )
  440. {
  441. delete pStore;
  442. }
  443. }
  444. m_aptrAssistant.RemoveAll( );
  445. }
  446. CSPTime CStDatabase::GetTimeInitial( )
  447. {
  448. return CSPTime( 1990, 12, 19, 0, 0, 0 );
  449. }
  450. BOOL CStDatabase::GetTimeLocalRange( CSPTime *ptmLatest, CSPTime * ptmPioneer, CSPTime * ptmInitial )
  451. {
  452. CStock stock;
  453. stock.SetStockCode( CStock::marketSHSE, STKLIB_CODE_MAIN );
  454. stock.SetDatabase( this );
  455. if( !stock.PrepareData( CStock::dataK, CKData::ktypeDay ) )
  456. return FALSE;
  457. CKData & kday = stock.GetKDataDay();
  458. int nYear, nMonth, nDay, nHour, nMinute;
  459. if( ptmLatest )
  460. {
  461. if( !kday.LatestDate( nYear, nMonth, nDay, nHour, nMinute ) )
  462. return FALSE;
  463. *ptmLatest = CSPTime( nYear, nMonth, nDay, 23, 59, 59 );
  464. }
  465. if( ptmPioneer )
  466. {
  467. if( kday.GetSize() == 0 || !kday.DateAt(0, nYear, nMonth, nDay, nHour, nMinute ) )
  468. return FALSE;
  469. *ptmPioneer = CSPTime( nYear, nMonth, nDay, 0, 0, 0 );
  470. }
  471. if( ptmInitial )
  472. {
  473. *ptmInitial = GetTimeInitial( );
  474. }
  475. return TRUE;
  476. }
  477. BOOL CStDatabase::GetNeedDownloadRange( CStockInfo &info, CSPTime tmBegin, CSPTime tmEnd, CSPTime &tmDLBegin, CSPTime &tmDLEnd )
  478. {
  479. tmDLBegin = tmBegin;
  480. tmDLEnd = tmEnd;
  481. // Prepare Data
  482. CStock stock;
  483. stock.SetStockInfo( &info );
  484. stock.SetDatabase( this );
  485. if( !stock.PrepareData( CStock::dataK, CKData::ktypeDay ) )
  486. return TRUE;
  487. CKData & kday = stock.GetKDataDay();
  488. // Prepare Time
  489. CSPTime tmInitial, tmLatest, tmPioneer;
  490. CSPTime sptimeInitial;
  491. if( 0 != info.m_datebegin && sptimeInitial.FromStockTimeDay( info.m_datebegin ) )
  492. tmInitial = sptimeInitial.GetTime();
  493. else
  494. tmInitial = GetTimeInitial( );
  495. int nYear, nMonth, nDay, nHour, nMinute;
  496. if( !kday.LatestDate( nYear, nMonth, nDay, nHour, nMinute ) )
  497. return TRUE;
  498. tmLatest = CSPTime( nYear, nMonth, nDay, 23, 59, 59 );
  499. if( kday.GetSize() == 0 || !kday.DateAt(0, nYear, nMonth, nDay, nHour, nMinute ) )
  500. return TRUE;
  501. tmPioneer = CSPTime( nYear, nMonth, nDay, 0, 0, 0 );
  502. // Deal With
  503. if( tmBegin < tmInitial )
  504. tmBegin = tmInitial;
  505. if( tmBegin >= tmPioneer && tmEnd <= tmLatest )
  506. {
  507. int nCount = 0;
  508. for( int k=0; k<kday.GetSize(); k++ )
  509. {
  510. DWORD date = kday.ElementAt(k).m_date;
  511. CSPTime sptime;
  512. if( sptime.FromStockTimeDay(date) )
  513. {
  514. if( sptime.GetTime() >= tmBegin.GetTime() && sptime.GetTime() <= tmEnd.GetTime() )
  515. nCount ++;
  516. }
  517. }
  518. CSPTimeSpan span = tmEnd - tmBegin;
  519. if( nCount > span.GetDays()*4/7 )
  520. return FALSE;
  521. }
  522. if( tmEnd <= tmPioneer )
  523. {
  524. tmDLBegin = tmBegin;
  525. tmDLEnd = tmPioneer-CSPTimeSpan(1,0,0,0);
  526. }
  527. else if( tmBegin >= tmLatest )
  528. {
  529. tmDLBegin = tmLatest+CSPTimeSpan(1,0,0,0);
  530. tmDLEnd = tmEnd;
  531. }
  532. else if( tmBegin < tmPioneer && tmEnd > tmPioneer && tmEnd <= tmLatest )
  533. {
  534. tmDLBegin = tmBegin;
  535. tmDLEnd = tmPioneer-CSPTimeSpan(1,0,0,0);
  536. }
  537. else if( tmBegin >= tmPioneer && tmBegin < tmLatest && tmEnd > tmLatest )
  538. {
  539. tmDLBegin = tmLatest+CSPTimeSpan(1,0,0,0);
  540. tmDLEnd = tmEnd;
  541. }
  542. else
  543. {
  544. tmDLBegin = tmBegin;
  545. tmDLEnd = tmEnd;
  546. }
  547. return TRUE;
  548. }
  549. // 将钱龙格式K线数据 加入 通用数据包
  550. int CStDatabase::AppendToTyData( const char *code, const char *name, int nKType, LPCTSTR lpszKFile, LPCTSTR lpszTyDataFile, time_t tmBegin, time_t tmEnd )
  551. {
  552. int nCount = 0;
  553. CSPFile fileK, fileTy;
  554. if( fileK.Open( lpszKFile, CSPFile::modeRead )
  555. && fileTy.Open( lpszTyDataFile, CSPFile::modeCreate|CSPFile::modeNoTruncate|CSPFile::modeReadWrite ) )
  556. {
  557. // Init Header
  558. TYDAY_FHEADER header;
  559. memset( &header, 0, sizeof(header) );
  560. header.magic = 0x06;
  561. for( int i=0; i<sizeof(header.code); i++ )
  562. header.code[i] = ' ';
  563. header.magic2 = 0x08;
  564. for( i=0; i<sizeof(header.name); i++ )
  565. header.name[i] = ' ';
  566. CSPTime sptime = CSPTime::GetCurrentTime();
  567. header.date = sptime.ToStockTimeDay();
  568. header.datebegin= header.date;
  569. header.dateend = header.date;
  570. header.gendate = header.date;
  571. header.gentime = sptime.GetTime();
  572. if( sizeof(header) != fileTy.Read( &header, sizeof(header) ) )
  573. {
  574. fileTy.SeekToBegin();
  575. fileTy.Write( &header, sizeof(header) );
  576. }
  577. header.from = 'CL';
  578. fileTy.SeekToEnd();
  579. // generate
  580. if( CKData::IsDayOrMin(nKType) )
  581. {
  582. DWORD dateBegin = CSPTime(tmBegin).ToStockTimeDay();
  583. DWORD dateEnd = CSPTime(tmEnd).ToStockTimeDay();
  584. struct QL_Data_day qlkd;
  585. while( sizeof(qlkd) == fileK.Read( &qlkd, sizeof(qlkd) ) )
  586. {
  587. if( qlkd.day_date < dateBegin || qlkd.day_date > dateEnd )
  588. continue;
  589. KDATA kd;
  590. TYDAY_RECORD tyrecord;
  591. convert_QL_Data_day_to_KDATA( CStock::marketUnknown, code, &qlkd, &kd );
  592. convert_KDATA_to_TYDAY_RECORD( header.recordcount+1, name, &kd, &tyrecord );
  593. fileTy.Write( &tyrecord, sizeof(tyrecord) );
  594. // Modified header
  595. if( tyrecord.date < header.datebegin )
  596. header.datebegin = tyrecord.date;
  597. if( tyrecord.date > header.dateend )
  598. header.dateend = tyrecord.date;
  599. header.recordcount += 1;
  600. nCount ++;
  601. }
  602. }
  603. else
  604. {
  605. DWORD dateBegin = CSPTime(tmBegin).ToStockTimeMin();
  606. DWORD dateEnd = CSPTime(tmEnd).ToStockTimeMin();
  607. struct QL_Data_5min qlkd;
  608. while( sizeof(qlkd) == fileK.Read( &qlkd, sizeof(qlkd) ) )
  609. {
  610. if( qlkd.min_off < dateBegin || qlkd.min_off > dateEnd )
  611. continue;
  612. KDATA kd;
  613. TYDAY_RECORD tyrecord;
  614. convert_QL_Data_5min_to_KDATA( CStock::marketUnknown, code, &qlkd, &kd );
  615. convert_KDATA_to_TYDAY_RECORD_MIN( header.recordcount+1, name, &kd, &tyrecord );
  616. fileTy.Write( &tyrecord, sizeof(tyrecord) );
  617. // Modified header
  618. if( tyrecord.date < header.datebegin )
  619. header.datebegin = tyrecord.date;
  620. if( tyrecord.date > header.dateend )
  621. header.dateend = tyrecord.date;
  622. header.recordcount += 1;
  623. nCount ++;
  624. }
  625. }
  626. if( nCount > 0 )
  627. header.sharecount += 1;
  628. fileTy.SeekToBegin();
  629. fileTy.Write( &header, sizeof(header) );
  630. fileK.Close();
  631. fileTy.Close();
  632. }
  633. return nCount;
  634. }