00001 #pragma ident "$Id: FileSpec.cpp 3143 2012-06-19 16:19:50Z snelsen $"
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00051 #include <algorithm>
00052
00053 #include "FileSpec.hpp"
00054 #include "TimeString.hpp"
00055 #include "StringUtils.hpp"
00056
00057 using namespace std;
00058 using namespace gpstk;
00059 using namespace gpstk::StringUtils;
00060
00061 namespace gpstk
00062 {
00063
00064 FileSpec::FileSpecType& operator-- (FileSpec::FileSpecType& fst, int)
00065 {
00066 return fst = (fst == FileSpec::unknown) ?
00067 FileSpec::end : FileSpec::FileSpecType(fst-1);
00068 }
00069
00070
00071 FileSpec::FileSpecType& operator++ (FileSpec::FileSpecType& fst, int)
00072 {
00073 return fst = (fst == FileSpec::end) ?
00074 FileSpec::unknown : FileSpec::FileSpecType(fst+1);
00075 }
00076
00077
00078 bool FileSpec::FileSpecSort::operator() (const std::string& l,
00079 const std::string& r) const
00080 {
00081
00082 std::string tl(l, offset + l.find_last_of(slash) + 1, length);
00083 std::string tr(r, offset + r.find_last_of(slash) + 1, length);
00084 if (sortBy == ascending)
00085 return tl < tr;
00086 else
00087 return tl > tr;
00088 }
00089
00090 string FileSpec::convertFileSpecType(const FileSpecType fst)
00091 throw(FileSpecException)
00092 {
00093 if (fst == station) return string("n");
00094 else if (fst == receiver) return string("r");
00095 else if (fst == prn) return string("p");
00096 else if (fst == selected) return string("t");
00097 else if (fst == sequence) return string("I");
00098 else if (fst == version) return string("v");
00099 else if (fst == fixed) return string("");
00100 else if (fst == clock) return string("k");
00101 else if (fst == text) return string("x");
00102
00103 else if (fst == year) return string("y");
00104 else if (fst == month) return string("m");
00105 else if (fst == dayofmonth) return string("d");
00106 else if (fst == hour) return string("H");
00107 else if (fst == minute) return string("M");
00108 else if (fst == second) return string("S");
00109 else if (fst == fsecond) return string("f");
00110 else if (fst == gpsweek) return string("G");
00111 else if (fst == fullgpsweek) return string("F");
00112 else if (fst == gpssecond) return string("g");
00113 else if (fst == mjd) return string("Q");
00114 else if (fst == dayofweek) return string("w");
00115 else if (fst == day) return string("j");
00116 else if (fst == doysecond) return string("s");
00117 else if (fst == zcount) return string("Z");
00118 else if (fst == zcountfloor) return string("z");
00119 else if (fst == unixsec) return string("U");
00120 else if (fst == unixusec) return string("u");
00121 else if (fst == fullzcount) return string("C");
00122 else
00123 {
00124 FileSpecException fse("Unknown FileSpecType: " + asString(fst));
00125 GPSTK_THROW(fse);
00126 }
00127 }
00128
00129 FileSpec::FileSpecType FileSpec::convertFileSpecType(const string& fst)
00130 throw(FileSpecException)
00131 {
00132 if (fst == string("n")) return station;
00133 else if (fst == string("r")) return receiver;
00134 else if (fst == string("p")) return prn;
00135 else if (fst == string("t")) return selected;
00136 else if (fst == string("I")) return sequence;
00137 else if (fst == string("v")) return version;
00138 else if (fst == string("k")) return clock;
00139 else if (fst == string("x")) return text;
00140
00141 else if (fst == string("Y") ||
00142 fst == string("y")) return year;
00143 else if (fst == string("m")) return month;
00144 else if (fst == string("d")) return dayofmonth;
00145 else if (fst == string("H")) return hour;
00146 else if (fst == string("M")) return minute;
00147 else if (fst == string("S")) return second;
00148 else if (fst == string("f")) return fsecond;
00149 else if (fst == string("G")) return gpsweek;
00150 else if (fst == string("F")) return fullgpsweek;
00151 else if (fst == string("g")) return gpssecond;
00152 else if (fst == string("Q")) return mjd;
00153 else if (fst == string("w")) return dayofweek;
00154 else if (fst == string("j")) return day;
00155 else if (fst == string("s")) return doysecond;
00156 else if (fst == string("Z")) return zcount;
00157 else if (fst == string("z")) return zcountfloor;
00158 else if (fst == string("U")) return unixsec;
00159 else if (fst == string("u")) return unixusec;
00160 else if (fst == string("C") ||
00161 fst == string("c")) return fullzcount;
00162 else
00163 {
00164 FileSpecException fse("Unknown FileSpecType: " + fst);
00165 GPSTK_THROW(fse);
00166 }
00167 }
00168
00169
00170 string FileSpec::createSearchString() const
00171 throw(FileSpecException)
00172 {
00173 string searchString;
00174
00175
00176 vector<FileSpecElement>::const_iterator itr = fileSpecList.begin();
00177 while (itr != fileSpecList.end())
00178 {
00179
00180 if ( ((*itr).type <= unknown) || ((*itr).type >= end) )
00181 {
00182 FileSpecException fse("Unknown FileSpecType: " +
00183 asString((*itr).type));
00184 GPSTK_THROW(fse);
00185 }
00186
00187 else if ((*itr).type == fixed)
00188 {
00189 searchString += (*itr).field;
00190 }
00191
00192 else
00193 {
00194 searchString += string((*itr).numCh, '?');
00195 }
00196
00197 itr++;
00198 }
00199
00200 return searchString;
00201 }
00202
00203 string FileSpec::extractField(const string& filename,
00204 const FileSpecType fst) const
00205 throw(FileSpecException)
00206 {
00207
00208 if ((fst <= unknown) || (fst >= end))
00209 {
00210 FileSpecException fse("Unknown FileSpecType: " +
00211 convertFileSpecType(fst));
00212 GPSTK_THROW(fse);
00213 }
00214
00215
00216 vector<FileSpecElement>::const_iterator itr = fileSpecList.begin();
00217 while (itr != fileSpecList.end())
00218 {
00219
00220 if ((*itr).type == fst)
00221 {
00222 return filename.substr((*itr).offset, (*itr).numCh);
00223 }
00224
00225
00226 itr++;
00227 }
00228
00229 FileSpecException fse("Couldn't find specified FileSpecType: " +
00230 convertFileSpecType(fst));
00231 GPSTK_THROW(fse);
00232 }
00233
00234 bool FileSpec::hasField(const FileSpecType fst) const
00235 throw(FileSpecException)
00236 {
00237 vector<FileSpecElement>::const_iterator itr = fileSpecList.begin();
00238 while (itr != fileSpecList.end())
00239 {
00240
00241 if (((*itr).type <= unknown) || ((*itr).type >= end))
00242 {
00243 FileSpecException fse("Unknown FileSpecType: " +
00244 convertFileSpecType((*itr).type));
00245 GPSTK_THROW(fse);
00246 }
00247 if ((*itr).type == fst)
00248 return true;
00249 itr++;
00250 }
00251 return false;
00252 }
00253
00254
00255 CommonTime FileSpec::extractCommonTime(const string& filename) const
00256 throw(FileSpecException)
00257 {
00258
00259 try
00260 {
00261 CommonTime dt(0.L);
00262 mixedScanTime(dt, filename, fileSpecString);
00263 return dt;
00264 }
00265 catch(Exception& exc)
00266 {
00267
00268 FileSpecException fse(exc);
00269 fse.addText("Can't generate a CommonTime for this FileSpec");
00270 GPSTK_THROW(fse);
00271 }
00272 catch(std::exception& exc)
00273 {
00274 FileSpecException fse("std::exception: " + string(exc.what()));
00275 fse.addText("Can't generate a CommonTime for this FileSpec");
00276 GPSTK_THROW(fse);
00277 }
00278 catch(...)
00279 {
00280 FileSpecException fse("unknown exception");
00281 fse.addText("Can't generate a CommonTime for this FileSpec");
00282 GPSTK_THROW(fse);
00283 }
00284
00285 }
00286
00287 std::string FileSpec::toString(const gpstk::CommonTime& dt,
00288 const FSTStringMap& fstsMap) const
00289 {
00290 string toReturn;
00291
00292
00293
00294
00295
00296
00297 vector<FileSpecElement>::const_iterator fslItr = fileSpecList.begin();
00298 while (fslItr != fileSpecList.end())
00299 {
00300 FSTStringMap::const_iterator fstsItr = fstsMap.find((*fslItr).type);
00301
00302
00303 if (fstsItr != fstsMap.end())
00304 {
00305
00306 if ((*fstsItr).first == text)
00307 {
00308 toReturn += (*fstsItr).second;
00309 }
00310 else
00311 {
00312 toReturn +=
00313 rightJustify((*fstsItr).second, (*fslItr).numCh, '0');
00314 }
00315 }
00316 else
00317 {
00318 toReturn += (*fslItr).field;
00319 }
00320
00321 fslItr++;
00322 }
00323
00324 toReturn = printTime(dt,toReturn);
00325
00326 return toReturn;
00327 }
00328
00329 void FileSpec::sortList(vector<string>& fileList,
00330 const FileSpecSortType fsst) const
00331 throw(FileSpecException)
00332 {
00333
00334
00335 for(FileSpecType fst = FileSpecType(end-1); fst > unknown; fst--)
00336 {
00337 if (hasField(fst))
00338 {
00339
00340 vector<FileSpecElement>::const_iterator itr = fileSpecList.begin();
00341 string::size_type ofs, len;
00342 while (itr != fileSpecList.end())
00343 {
00344
00345 if ((*itr).type == fst)
00346 {
00347 ofs = (*itr).offset;
00348 len = (*itr).numCh;
00349 if (fsst != none)
00350 {
00351 FileSpecSort q(ofs, len, fsst);
00352 stable_sort(fileList.begin(), fileList.end(), q);
00353 }
00354 }
00355
00356
00357 itr++;
00358 }
00359 }
00360 }
00361
00362
00363
00364
00365
00366
00367
00368
00369
00370
00371
00372
00373
00374
00375
00376 if (hasField(version))
00377 {
00378
00379 vector<string> copyOfFileList = fileList;
00380
00381
00382 vector<FileSpecElement>::const_iterator itr = fileSpecList.begin();
00383 vector<FileSpecElement> versionVec;
00384 while (itr != fileSpecList.end())
00385 {
00386 if ((*itr).type == version)
00387 versionVec.push_back(*itr);
00388 itr++;
00389 }
00390
00391
00392 vector<string>::size_type index;
00393 for (index = 0; index < copyOfFileList.size(); index++)
00394 {
00395 string::size_type slashpos = copyOfFileList[index].rfind(slash);
00396 if (slashpos != string::npos)
00397 copyOfFileList[index].erase(0, slashpos + 1);
00398 copyOfFileList[index].erase(versionVec[0].offset,
00399 versionVec[0].numCh);
00400 }
00401
00402
00403
00404
00405
00406
00407
00408 map<string, string> versionMap;
00409 for (index = 0; index < copyOfFileList.size(); index++)
00410 versionMap[copyOfFileList[index]] = fileList[index];
00411
00412 fileList.erase(fileList.begin(), fileList.end());
00413 map<string, string>::iterator mapitr = versionMap.begin();
00414 while (mapitr != versionMap.end())
00415 {
00416 fileList.push_back((*mapitr).second);
00417 mapitr++;
00418 }
00419 }
00420 }
00421
00422 void FileSpec::dump(ostream& o) const
00423 {
00424 o << "FileSpec string: " << fileSpecString << endl;
00425
00426 o << "offset numch type field" << endl;
00427 vector<FileSpecElement>::const_iterator itr = fileSpecList.begin();
00428 while (itr != fileSpecList.end())
00429 {
00430 o << setw(6) << (*itr).offset << setw(6) << (*itr).numCh
00431 << setw(6) << convertFileSpecType((*itr).type)
00432
00433
00434 << setw(6 + ((*itr).field.size() > 5 ? ((*itr).field.size()-5): 0))
00435 << (*itr).field << endl;
00436 itr++;
00437 }
00438 }
00439
00440 void FileSpec::init(const string& fileSpec)
00441 throw(FileSpecException)
00442 {
00443 try
00444 {
00445 fileSpecList.clear();
00446 fileSpecString.clear();
00447
00448 fileSpecString = fileSpec;
00449
00450
00451
00452 string::size_type offset = 0;
00453
00454
00455 string fs(fileSpec);
00456
00457
00458
00459 while (!fs.empty())
00460 {
00461 string atom;
00462
00463
00464 string::size_type pos = fs.find('%');
00465 atom = fs.substr(0,pos);
00466 fs.erase(0,pos);
00467
00468
00469
00470
00471 if (fs.empty())
00472 {
00473 if (!atom.empty())
00474 {
00475 FileSpecElement fse(atom.size(), offset, fixed, atom);
00476 fileSpecList.push_back(fse);
00477 }
00478 }
00479
00480
00481 else
00482 {
00483 if (!atom.empty())
00484 {
00485 FileSpecElement fse(atom.size(), offset, fixed, atom);
00486 fileSpecList.push_back(fse);
00487 offset += atom.size();
00488 atom.erase(atom.begin(), atom.end());
00489 }
00490
00491
00492
00493
00494 atom += fs[0];
00495 fs.erase(0,1);
00496
00497
00498
00499 int numChs = asInt(fs);
00500 if (numChs == 0)
00501 numChs = 1;
00502
00503 if (fs[0] == '0')
00504 atom += '0';
00505
00506 stripLeading(fs, "0");
00507 stripLeading(fs, asString(numChs));
00508
00509 atom += asString(numChs);
00510
00511
00512 FileSpecType fst = convertFileSpecType(fs.substr(0,1));
00513 atom += fs[0];
00514
00515
00516 if ((fs.substr(0,1) == string("Y")) && (numChs != 4))
00517 numChs = 4;
00518 fs.erase(0,1);
00519
00520 FileSpecElement fse(numChs, offset, fst, atom);
00521 fileSpecList.push_back(fse);
00522 offset += numChs;
00523 }
00524
00525 }
00526 }
00527 catch(FileSpecException& e)
00528 {
00529 e.addText("Check your file spec for errors: " + fileSpec);
00530 GPSTK_RETHROW(e);
00531 }
00532 catch(StringException& e)
00533 {
00534 FileSpecException fse(e);
00535 fse.addText("String exception: Check the file spec for errors: " + fileSpec);
00536 GPSTK_THROW(fse);
00537 }
00538 catch(std::exception& e)
00539 {
00540 FileSpecException fse("std::exception: " + string(e.what()));
00541 fse.addText("Check the file spec for errors: " + fileSpec);
00542 GPSTK_THROW(fse);
00543 }
00544 catch(...)
00545 {
00546 FileSpecException fse("Unknown exception: Check the file spec for errors: " + fileSpec);
00547 GPSTK_THROW(fse);
00548 }
00549 }
00550
00551 }