MSCStore.cpp

Go to the documentation of this file.
00001 #pragma ident "$Id: MSCStore.cpp 2452 2010-08-12 14:52:08Z afarris $"
00002 
00003 //============================================================================
00004 //
00005 //  This file is part of GPSTk, the GPS Toolkit.
00006 //
00007 //  The GPSTk is free software; you can redistribute it and/or modify
00008 //  it under the terms of the GNU Lesser General Public License as published
00009 //  by the Free Software Foundation; either version 2.1 of the License, or
00010 //  any later version.
00011 //
00012 //  The GPSTk is distributed in the hope that it will be useful,
00013 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
00014 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00015 //  GNU Lesser General Public License for more details.
00016 //
00017 //  You should have received a copy of the GNU Lesser General Public
00018 //  License along with GPSTk; if not, write to the Free Software Foundation,
00019 //  Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00020 //  
00021 //  Copyright 2004, The University of Texas at Austin
00022 //
00023 //============================================================================
00024 
00030 #include <iostream>
00031 #include <fstream>
00032 #include <iomanip>
00033 
00034 #include "StringUtils.hpp"
00035 #include "MSCStore.hpp"
00036 #include "MathBase.hpp"
00037 
00038 using namespace std;
00039 using namespace gpstk;
00040 using gpstk::StringUtils::asString;
00041 
00042 namespace gpstk
00043 {
00044       // The number o seconds in a year is 365 and a quetar days time
00045       // the number of seconds in a day.
00046    const double MSCStore::SEC_YEAR = 365.25 * DayTime::SEC_DAY;
00047    
00048    //--------------------------------------------------------------------------
00049    //--------------------------------------------------------------------------
00050    Xvt MSCStore::getXvt(const std::string stationID, const DayTime& t)
00051       const throw(InvalidRequest)
00052    {
00053       try
00054       {
00055             // Find an appropriate MSCData object.  
00056          const MSCData& msc = findMSC( stationID, t ); 
00057 
00058          return( msc.getXvt(t) );
00059       }
00060       catch(InvalidRequest& ir)
00061       {
00062          GPSTK_RETHROW(ir);
00063       }
00064    } // end of MSCStore::getXvt()
00065 
00066    Xvt MSCStore::getXvt(unsigned long stationIDno, const DayTime& t)
00067       const throw(InvalidRequest)
00068    {
00069       try
00070       {
00071             // Find an appropriate MSCData object.  
00072          const MSCData& msc = findMSC( stationIDno, t ); 
00073 
00074          return( msc.getXvt(t) );
00075       }
00076       catch(InvalidRequest& ir)
00077       {
00078          GPSTK_RETHROW(ir);
00079       }
00080    } // end of MSCStore::getXvt()
00081 
00082    //--------------------------------------------------------------------------
00083    //--------------------------------------------------------------------------
00084    void MSCStore::dump(std::ostream& s, short detail) const
00085       throw()
00086    {
00087       MMci it;
00088 
00089       s << "Dump of MSCStore:\n";
00090       if (detail==0)
00091       {
00092          unsigned msc_count=0;
00093          for (it = mscMap.begin(); it != mscMap.end(); it++)
00094          {
00095             msc_count += it->second.size();
00096          }
00097          s << " Span is " << initialTime
00098            << " to " << finalTime
00099            << " with " << msc_count << " entries."
00100            << std::endl;
00101       }
00102       else
00103       {
00104          for (it = mscMap.begin(); it != mscMap.end(); it++)
00105          {
00106             s << "Coordinates for station '" << (std::string) it->first << "'" << endl;
00107             SMMci it2;
00108             for (it2 = it->second.begin(); it2 != it->second.end(); ++it2)
00109             {
00110                const MSCData& em = it2->second;
00111 
00112                s << "Mnemonic    " << em.mnemonic
00113                  << ", Ref epoch   " << em.refepoch
00114                  << ", Eff epoch   " << em.effepoch
00115                  << ", Coordinates " << em.coordinates
00116                  << ", Velocities  " << em.velocities   
00117                  << std::endl;
00118             }
00119          }
00120          s << "  End of MSCStore data." << std::endl << std::endl;
00121       }
00122    } // end of MSCStore::dump()
00123 
00124 //-----------------------------------------------------------------------------
00125 //
00126 //  edit() is a little unusual in that the MSCData objects have a beginning-of-
00127 //  effectivity, but do NOT have an end-of-effectivity.  Therefore, we end up
00128 //  with the following sort of logic (BOT = BEGINNING_OF_TIME, EOT = END_OF_TIME).
00129 //
00130 // Case    tmin          tmax          action
00131 //   1     BOT           EOT           no action
00132 //   2     BOT           <initialTime  clear all 
00133 //   3     >finalTime    EOT           keep last entry for each station
00134 //                                     (no ending effectivity)
00135 //   4     >initialTime  EOT           clear if effepoch < tmin && 
00136 //         <finalTime                  not ending object
00137 //   5     BOT           >initialTime  clear if effepoch > tmax
00138 //                       <finalTime
00139 //   6     >initialTime  >initialTime  clear if (effepoch > tmax or 
00140 //         <finalTime    <finalTime             (effepoch < tmin and
00141 //         <tmax         >tmax                   not ending object)
00142 //
00143 //   Cases 1-5 are degenerate examples of case 6.
00144 //
00145 //-----------------------------------------------------------------------------
00146    void MSCStore::edit(const DayTime& tmin, const DayTime& tmax)
00147       throw()
00148    {
00149       
00150          // For each station....      
00151       MMi mmi;
00152       for(mmi = mscMap.begin(); mmi != mscMap.end(); mmi++)
00153       {
00154             // If the effective epoch of the final entry is beyond
00155             // tmax, clear all objects
00156          StaMSCMap& smmr = mmi->second;
00157          StaMSCMap::reverse_iterator smmir;
00158          smmir = smmr.rbegin();
00159          if (smmir->first > tmax) 
00160          {
00161             smmr.clear();   
00162          }
00163             // Since we're in the else branch, there's at least
00164             // one entry that needs to be retained.
00165          else 
00166          {
00167             SMMi smmi = smmr.begin();
00168             SMMi lastTooEarly = smmi;// Just initialize to a valid value 
00169             while (smmi != smmr.end() && smmi->first < tmin)
00170             {
00171                lastTooEarly = smmi;
00172                ++smmi;
00173             }
00174             if (smmi != smmr.begin()) smmr.erase( smmr.begin(), lastTooEarly );
00175          }
00176       }
00177       initialTime = tmin;
00178       
00179    } // end of MSCStore::edit()
00180 
00181    //--------------------------------------------------------------------------
00182    //--------------------------------------------------------------------------
00183    void MSCStore::loadFile(const std::string& filename)
00184       throw(FileMissingException)
00185    {
00186       try
00187       {
00188          MSCStream strm(filename.c_str());
00189          if (!strm)
00190          {
00191             FileMissingException e("File " + filename + " could not be opened.");
00192             GPSTK_THROW(e);
00193          }
00194          
00195          MSCHeader header;
00196          strm >> header;
00197          addFile(filename, header);  // <<<---- Error here
00198          
00199          MSCData rec;
00200          while(strm >> rec)
00201          {
00202                  addMSC(rec);
00203          }       
00204       }
00205       catch (gpstk::Exception& e)
00206       {
00207          GPSTK_RETHROW(e);
00208       } 
00209    }
00210 
00211    //--------------------------------------------------------------------------
00212    //--------------------------------------------------------------------------
00213    bool MSCStore::addMSC(const MSCData& msc)
00214       throw()
00215    {
00216          // Chop off any leading/trailing whitespace
00217       std::string key = StringUtils::stripTrailing(msc.mnemonic);
00218       key = StringUtils::stripLeading(key);
00219       
00220       StaMSCMap& mm = mscMap[key];
00221       mm[msc.effepoch] = msc;
00222       
00223       if (msc.effepoch < initialTime) initialTime = msc.effepoch;
00224       // NOTE: finalTime is purposely left at END_OF_TIME - 
00225       // MSCData objects have no ending time of effectivity.
00226       return(true);
00227    }
00228 
00229    //--------------------------------------------------------------------------
00230    //--------------------------------------------------------------------------
00231    const MSCData&
00232    MSCStore::findMSC(const unsigned long stationID, const DayTime& t) 
00233       const throw(InvalidRequest)
00234    {
00235       try
00236       {
00237          std::string sid = StringUtils::asString( stationID );
00238          return( findMSC( sid, t ));
00239       }
00240       catch(InvalidRequest& ir)
00241       {
00242          GPSTK_RETHROW(ir);
00243       }
00244    }
00245    //--------------------------------------------------------------------------
00246    //--------------------------------------------------------------------------
00247    const MSCData&
00248    MSCStore::findMSC(const std::string stationID, const DayTime& t) 
00249       const throw(InvalidRequest)
00250    {
00251       try
00252       {
00253          std::string key = StringUtils::stripTrailing( stationID );
00254          key = StringUtils::stripLeading( key ); 
00255          MMci mm = mscMap.find( key );
00256 
00257          // Didn't find the station under the mnemonic.
00258             // Check for a possible station number use.
00259          if (mm == mscMap.end() && StringUtils::isDigitString(key) )
00260          {
00261             unsigned long staNum = StringUtils::asUnsigned(key);
00262             mm=mscMap.begin();
00263             while (mm != mscMap.end())
00264             {
00265                const StaMSCMap& smm = mm->second;
00266                SMMci smmi = smm.begin();
00267                if (smmi->second.station == staNum) break;
00268                ++mm;
00269             }
00270          }
00271          if (mm==mscMap.end())
00272          {
00273             InvalidRequest e("No station coordinates for station '" + key + "'" );
00274             GPSTK_THROW(e);
00275          }
00276          
00277             // If we reach this point, mm should hold a valid reference
00278             // to an StaMSCMap object.  Now to find the appropriate
00279             // entry in that object.
00280             // The effective epoch (which is the key for the list) represents
00281             // the earliest time that the MSCData object is applicable.  There
00282             // is no corresponding end time.  Therefore, we'll start at the 
00283             // END of the time-ordered list and select the first object
00284             // with a key <= the time of interest.  
00285             //
00286          StaMSCMap::const_reverse_iterator smmir;
00287          for (smmir = mm->second.rbegin(); smmir != mm->second.rend(); ++smmir)
00288          {
00289             const DayTime& dtr = smmir->first;
00290             if (dtr<=t) return( smmir->second );
00291          }
00292 
00293             // If we reach this point, there's no time-approprate entry for 
00294             // this station
00295          InvalidRequest e("No station coordinates for station " + 
00296                            stationID + " at time " +
00297                            t.printf("%02m/%02d/%02y") );
00298          GPSTK_THROW(e);
00299       }
00300       catch(InvalidRequest& ir)
00301       {
00302          GPSTK_RETHROW(ir);
00303       }
00304    }
00305 
00306 //-----------------------------------------------------------------------------
00307 //-----------------------------------------------------------------------------
00308    unsigned MSCStore::size() const throw()
00309    {
00310       unsigned counter = 0;
00311       for(MMci i = mscMap.begin(); i != mscMap.end(); ++i)
00312       {
00313          counter += i->second.size();
00314       }
00315       return counter;
00316    }
00317 
00318 
00319 //-----------------------------------------------------------------------------
00320 //-----------------------------------------------------------------------------
00321    int MSCStore::addToList(std::list<MSCData>& v) const throw()
00322    {
00323       int n=0;
00324       for (MMci i = mscMap.begin(); i != mscMap.end(); ++i)
00325       {
00326          SMMci i2;
00327          for (i2=i->second.begin(); i2 != i->second.end(); ++i2)
00328          {
00329             v.push_back(i2->second);
00330             n++;
00331          }
00332       }
00333       return n;
00334    }
00335 
00336 
00337 //-----------------------------------------------------------------------------
00338 //-----------------------------------------------------------------------------
00339    list<std::string> MSCStore::getIDList()
00340    {
00341       list<std::string> temp;
00342       MMci mmci;
00343       for(mmci = mscMap.begin(); mmci != mscMap.end(); mmci++)
00344       {
00345          temp.push_back(mmci->first);
00346       }
00347       return(temp);
00348    }
00349 
00350    
00351 } // namespace
00352  

Generated on Tue May 22 03:31:00 2012 for GPS ToolKit Software Library by  doxygen 1.3.9.1