📄 mitab_datfile.cpp
字号:
{
nYear = atoi(papszTok[0]);
nMonth = atoi(papszTok[1]);
nDay = atoi(papszTok[2]);
}
else
{
nYear = atoi(papszTok[2]);
nMonth = atoi(papszTok[1]);
nDay = atoi(papszTok[0]);
}
}
else if (strlen(pszValue) == 0)
{
nYear = nMonth = nDay = 0;
}
else
{
CPLError(CE_Failure, CPLE_AppDefined,
"Invalid date field value `%s'. Date field values must "
"be in the format `YYYY/MM/DD', `MM/DD/YYYY' or `YYYYMMDD'",
pszValue);
CSLDestroy(papszTok);
return -1;
}
CSLDestroy(papszTok);
m_poRecordBlock->WriteInt16(nYear);
m_poRecordBlock->WriteByte(nMonth);
m_poRecordBlock->WriteByte(nDay);
if (CPLGetLastErrorNo() != 0)
return -1;
// Update Index
if (poINDFile && nIndexNo > 0)
{
GByte *pKey = poINDFile->BuildKey(nIndexNo, (nYear*0x10000 +
nMonth * 0x100 + nDay));
if (poINDFile->AddEntry(nIndexNo, pKey, m_nCurRecordId) != 0)
return -1;
}
return 0;
}
/**********************************************************************
* TABDATFile::WriteTimeField()
*
* Write the date field value at the current position in the data
* block.
*
* A time field is a 4 byte binary value which represents the number
* of milliseconds since midnight.
*
* The expected input is a 10 chars string in the format "HH:MM:SS"
* or "HHMMSSmmm"
*
* Returns 0 on success, or -1 if the operation failed, in which case
* CPLError() will have been called.
**********************************************************************/
int TABDATFile::WriteTimeField(const char *pszValue,
TABINDFile *poINDFile, int nIndexNo)
{
int nHour, nMin, nSec, nMS;
GInt32 nS = -1;
char **papszTok = NULL;
if (m_poRecordBlock == NULL)
{
CPLError(CE_Failure, CPLE_AssertionFailed,
"Can't write field value: GetRecordBlock() has not been called.");
return -1;
}
/*-----------------------------------------------------------------
* Get rid of leading spaces.
*----------------------------------------------------------------*/
while ( *pszValue == ' ' ) { pszValue++; }
/*-----------------------------------------------------------------
* Try to automagically detect time format, one of:
* "HH:MM:SS", or "HHMMSSmmm"
*----------------------------------------------------------------*/
if (strlen(pszValue) == 8)
{
/*-------------------------------------------------------------
* "HH:MM:SS"
*------------------------------------------------------------*/
char szBuf[9];
strcpy(szBuf, pszValue);
szBuf[2]=0;
szBuf[5]=0;
nHour = atoi(szBuf);
nMin = atoi(szBuf+3);
nSec = atoi(szBuf+6);
nMS = 0;
nS = (nHour*3600+nMin*60+nSec)*1000+nMS;
}
else if (strlen(pszValue) == 9)
{
/*-------------------------------------------------------------
* "HHMMSSmmm"
*------------------------------------------------------------*/
char szBuf[4];
strncpy(szBuf,pszValue,2);
szBuf[2]=0;
nHour = atoi(szBuf);
strncpy(szBuf,pszValue+2,2);
szBuf[2]=0;
nMin = atoi(szBuf);
strncpy(szBuf,pszValue+4,2);
szBuf[2]=0;
nSec = atoi(szBuf);
strncpy(szBuf,pszValue+6,3);
szBuf[3]=0;
nMS = atoi(szBuf);
nS = (nHour*3600+nMin*60+nSec)*1000+nMS;
}
else if (strlen(pszValue) == 0)
{
nS = -1; // Write -1 to .DAT file if value is not set
}
else
{
CPLError(CE_Failure, CPLE_AppDefined,
"Invalid time field value `%s'. Time field values must "
"be in the format `HH:MM:SS', or `HHMMSSmmm'",
pszValue);
CSLDestroy(papszTok);
return -1;
}
CSLDestroy(papszTok);
m_poRecordBlock->WriteInt32(nS);
if (CPLGetLastErrorNo() != 0)
return -1;
// Update Index
if (poINDFile && nIndexNo > 0)
{
GByte *pKey = poINDFile->BuildKey(nIndexNo, (nS));
if (poINDFile->AddEntry(nIndexNo, pKey, m_nCurRecordId) != 0)
return -1;
}
return 0;
}
/**********************************************************************
* TABDATFile::WriteDateTimeField()
*
* Write the DateTime field value at the current position in the data
* block.
*
* A datetime field is a 8 bytes binary value in which the first byte is
* the day, followed by 1 byte for the month, and 2 bytes for the year.
* After this the time value is stored as a 4 byte integer
* (milliseconds since midnight)
*
* The expected input is a 10 chars string in the format "YYYY/MM/DD HH:MM:SS"
* or "DD/MM/YYYY HH:MM:SS" or "YYYYMMDDhhmmssmmm"
*
* Returns 0 on success, or -1 if the operation failed, in which case
* CPLError() will have been called.
**********************************************************************/
int TABDATFile::WriteDateTimeField(const char *pszValue,
TABINDFile *poINDFile, int nIndexNo)
{
int nDay, nMonth, nYear, nHour, nMin, nSec, nMS;
char **papszTok = NULL;
if (m_poRecordBlock == NULL)
{
CPLError(CE_Failure, CPLE_AssertionFailed,
"Can't write field value: GetRecordBlock() has not been called.");
return -1;
}
/*-----------------------------------------------------------------
* Get rid of leading spaces.
*----------------------------------------------------------------*/
while ( *pszValue == ' ' ) { pszValue++; }
/*-----------------------------------------------------------------
* Try to automagically detect date format, one of:
* "YYYY/MM/DD HH:MM:SS", "DD/MM/YYYY HH:MM:SS", or "YYYYMMDDhhmmssmmm"
*----------------------------------------------------------------*/
if (strlen(pszValue) == 17)
{
/*-------------------------------------------------------------
* "YYYYMMDDhhmmssmmm"
*------------------------------------------------------------*/
char szBuf[18];
strcpy(szBuf, pszValue);
nMS = atoi(szBuf+14);
szBuf[14]=0;
nSec = atoi(szBuf+12);
szBuf[12]=0;
nMin = atoi(szBuf+10);
szBuf[10]=0;
nHour = atoi(szBuf+8);
szBuf[8]=0;
nDay = atoi(szBuf+6);
szBuf[6] = 0;
nMonth = atoi(szBuf+4);
szBuf[4] = 0;
nYear = atoi(szBuf);
}
else if (strlen(pszValue) == 19 &&
(papszTok = CSLTokenizeStringComplex(pszValue, "/ :",
FALSE, FALSE)) != NULL &&
CSLCount(papszTok) == 6 &&
(strlen(papszTok[0]) == 4 || strlen(papszTok[2]) == 4) )
{
/*-------------------------------------------------------------
* Either "YYYY/MM/DD HH:MM:SS" or "DD/MM/YYYY HH:MM:SS"
*------------------------------------------------------------*/
if (strlen(papszTok[0]) == 4)
{
nYear = atoi(papszTok[0]);
nMonth= atoi(papszTok[1]);
nDay = atoi(papszTok[2]);
nHour = atoi(papszTok[3]);
nMin = atoi(papszTok[4]);
nSec = atoi(papszTok[5]);
nMS = 0;
}
else
{
nYear = atoi(papszTok[2]);
nMonth= atoi(papszTok[1]);
nDay = atoi(papszTok[0]);
nHour = atoi(papszTok[3]);
nMin = atoi(papszTok[4]);
nSec = atoi(papszTok[5]);
nMS = 0;
}
}
else if (strlen(pszValue) == 0)
{
nYear = nMonth = nDay = 0;
nHour = nMin = nSec = nMS = 0;
}
else
{
CPLError(CE_Failure, CPLE_AppDefined,
"Invalid date field value `%s'. Date field values must "
"be in the format `YYYY/MM/DD HH:MM:SS', "
"`MM/DD/YYYY HH:MM:SS' or `YYYYMMDDhhmmssmmm'",
pszValue);
CSLDestroy(papszTok);
return -1;
}
CSLDestroy(papszTok);
GInt32 nS = (nHour*3600+nMin*60+nSec)*1000+nMS;
m_poRecordBlock->WriteInt16(nYear);
m_poRecordBlock->WriteByte(nMonth);
m_poRecordBlock->WriteByte(nDay);
m_poRecordBlock->WriteInt32(nS);
if (CPLGetLastErrorNo() != 0)
return -1;
// Update Index
if (poINDFile && nIndexNo > 0)
{
// __TODO__ (see bug #1844)
// Indexing on DateTime Fields not currently supported, that will
// require passing the 8 bytes datetime value to BuildKey() here...
CPLAssert(FALSE);
GByte *pKey = poINDFile->BuildKey(nIndexNo, (nYear*0x10000 +
nMonth * 0x100 + nDay));
if (poINDFile->AddEntry(nIndexNo, pKey, m_nCurRecordId) != 0)
return -1;
}
return 0;
}
/**********************************************************************
* TABDATFile::WriteDecimalField()
*
* Write the decimal field value at the current position in the data
* block.
*
* A decimal field is a floating point value with a fixed number of digits
* stored as a character string.
*
* nWidth is the field length, as defined in the .DAT header.
*
* CPLError() will have been called if something fails.
**********************************************************************/
int TABDATFile::WriteDecimalField(double dValue, int nWidth, int nPrec,
TABINDFile *poINDFile, int nIndexNo)
{
const char *pszVal;
pszVal = CPLSPrintf("%*.*f", nWidth, nPrec, dValue);
if ((int)strlen(pszVal) > nWidth)
pszVal += strlen(pszVal) - nWidth;
// Update Index
if (poINDFile && nIndexNo > 0)
{
GByte *pKey = poINDFile->BuildKey(nIndexNo, dValue);
if (poINDFile->AddEntry(nIndexNo, pKey, m_nCurRecordId) != 0)
return -1;
}
return m_poRecordBlock->WriteBytes(nWidth, (GByte*)pszVal);
}
/**********************************************************************
* TABDATFile::Dump()
*
* Dump block contents... available only in DEBUG mode.
**********************************************************************/
#ifdef DEBUG
void TABDATFile::Dump(FILE *fpOut /*=NULL*/)
{
if (fpOut == NULL)
fpOut = stdout;
fprintf(fpOut, "----- TABDATFile::Dump() -----\n");
if (m_fp == NULL)
{
fprintf(fpOut, "File is not opened.\n");
}
else
{
fprintf(fpOut, "File is opened: %s\n", m_pszFname);
fprintf(fpOut, "m_numFields = %d\n", m_numFields);
fprintf(fpOut, "m_numRecords = %d\n", m_numRecords);
}
fflush(fpOut);
}
#endif // DEBUG
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -